summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJérémy Zurcher <jeremy@asynk.ch>2010-01-07 18:12:43 +0100
committerJérémy Zurcher <jeremy@asynk.ch>2010-01-07 18:12:43 +0100
commit8d738ccbbc809e48916ac69c439d91986204565e (patch)
tree26489c553301de32ec97425b077fad6f3cd8b189
parentde7ceedae12efca39ec9128e9accdbc3e6f416f9 (diff)
downloadlock_free-8d738ccbbc809e48916ac69c439d91986204565e.zip
lock_free-8d738ccbbc809e48916ac69c439d91986204565e.tar.gz
faster with a constant backoff and timespec struct as local function variable
-rw-r--r--lf_ring_buffer.c32
-rw-r--r--lf_ring_buffer.h9
-rw-r--r--lf_ring_buffer_test.c2
3 files changed, 12 insertions, 31 deletions
diff --git a/lf_ring_buffer.c b/lf_ring_buffer.c
index 30532fc..506b0af 100644
--- a/lf_ring_buffer.c
+++ b/lf_ring_buffer.c
@@ -62,6 +62,8 @@
#define _LOG_( ... )
#endif
+#define BACKOFF_NANO_SLEEP 100
+
/* initialize an empty lf_ring_buffer struct */
lf_ring_buffer_t* lf_ring_buffer_create( size_t n_buf ) {
/* alloc ring_buffer struct */
@@ -77,8 +79,6 @@ lf_ring_buffer_t* lf_ring_buffer_create( size_t n_buf ) {
r->n_buf = n_buf;
r->read_from = -1;
r->write_to = 0;
- r->write_delay = BACKOFF_DELAY_INIT;
- r->read_delay = BACKOFF_DELAY_INIT;
return r;
}
@@ -91,8 +91,7 @@ void lf_ring_buffer_destroy( lf_ring_buffer_t *r ) {
/* write data into the ring buffer */
int lf_ring_buffer_write( lf_ring_buffer_t *r, void *data, int flags ) {
int idx, next;
- struct timespec st;
- st.tv_sec=0;
+ struct timespec backoff;
/* reserve a buffer */
for(;;){
idx = r->write_to;
@@ -117,11 +116,9 @@ int lf_ring_buffer_write( lf_ring_buffer_t *r, void *data, int flags ) {
} else {
_LOG_("write: not available\n");
if(IS_NOT_BLOCKING(flags)) return -1;
- st.tv_nsec=r->write_delay;
- nanosleep(&st,NULL);
- if( !(BACKOFF_INC_NOT(flags)) ) {
- if(r->write_delay<BACKOFF_DELAY_MAX) r->write_delay+=BACKOFF_DELAY_INC;
- }
+ backoff.tv_sec = 0;
+ backoff.tv_nsec = BACKOFF_NANO_SLEEP;
+ nanosleep(&backoff,NULL);
}
}
/* try to set read_from on idx if it has not been initialized yet
@@ -134,17 +131,13 @@ int lf_ring_buffer_write( lf_ring_buffer_t *r, void *data, int flags ) {
/* fill this buffer and mark it as filled */
memcpy( r->buffer[idx].data, data, LFRB_DATA_SIZE );
LFRB_MARK_AS_FILLED( r->buffer[idx] );
- if( !(BACKOFF_INC_NOT(flags)) ) {
- if(r->write_delay>BACKOFF_DELAY_INIT) r->write_delay-=BACKOFF_DELAY_INC;
- }
return 0;
}
/* read data from the ring buffer */
int lf_ring_buffer_read( lf_ring_buffer_t *r, void *data, int flags ) {
int idx, next;
- struct timespec st;
- st.tv_sec=0;
+ struct timespec backoff;
if(r->read_from==-1) return -1;
for(;;) {
idx = r->read_from;
@@ -165,18 +158,13 @@ int lf_ring_buffer_read( lf_ring_buffer_t *r, void *data, int flags ) {
} else {
_LOG_("read: not available\n");
if(IS_NOT_BLOCKING(flags)) return -1;
- st.tv_nsec=r->read_delay;
- nanosleep(&st,NULL);
- if( !(BACKOFF_INC_NOT(flags)) ) {
- if(r->read_delay<BACKOFF_DELAY_MAX) r->read_delay+=BACKOFF_DELAY_INC;
- }
+ backoff.tv_sec = 0;
+ backoff.tv_nsec = BACKOFF_NANO_SLEEP;
+ nanosleep(&backoff,NULL);
}
}
/* finish the read process */
LFRB_MARK_AS_READ( r->buffer[idx] );
- if( !(BACKOFF_INC_NOT(flags)) ) {
- if(r->read_delay>BACKOFF_DELAY_INIT) r->read_delay-=BACKOFF_DELAY_INC;
- }
return 0;
}
diff --git a/lf_ring_buffer.h b/lf_ring_buffer.h
index 51d29e5..64bed4c 100644
--- a/lf_ring_buffer.h
+++ b/lf_ring_buffer.h
@@ -35,23 +35,14 @@ extern "C" {
#include <sys/types.h>
#include "lf_ring_buffer_data.h"
-#define BACKOFF_DELAY_INIT 100
-#define BACKOFF_DELAY_INC 100
-#define BACKOFF_DELAY_MAX 1000
-
#define LFRB_NO_BLOCK 1 /* if buffer is full, leave instead of try again and again */
#define IS_NOT_BLOCKING( flags ) ( (flags)&LFRB_NO_BLOCK )
-#define LFRB_NO_BACKOFF_INC 2 /* do not use BACKOFF_DELAY_X */
-#define BACKOFF_INC_NOT( flags ) ( (flags)&LFRB_NO_BACKOFF_INC )
-
typedef struct ring_buffer {
LFRB_BUFFER_TYPE *buffer; /* buffer data */
size_t n_buf; /* number of buffers */
int read_from; /* index where to read data from */
int write_to; /* index where to write data to */
- int write_delay; /* backoff nanosleep to reduce fast looping when writing */
- int read_delay; /* backoff nanosleep to reduce fast looping when reading */
} lf_ring_buffer_t;
/* return an initialized lf_ring_buffer_t struct */
diff --git a/lf_ring_buffer_test.c b/lf_ring_buffer_test.c
index b3ec016..b7a7d30 100644
--- a/lf_ring_buffer_test.c
+++ b/lf_ring_buffer_test.c
@@ -138,12 +138,14 @@ int main( int argc, char** argv ) {
printf("parallel blocking read operations ...\n");
sequential_reads( ring, b_len, 0 );
}
+ /*
for(i=5; i<=100;i*=22) {
printf("%d parallel blocking with no backoff inc write operations .... \n",i);
parallel_writes( i, ring, b_len, LFRB_NO_BACKOFF_INC );
printf("parallel blocking read operations ...\n");
sequential_reads( ring, b_len, LFRB_NO_BACKOFF_INC );
}
+ */
for(i=5; i<=100;i*=22) {
printf("%d parallel non blocking write operations .... \n",i);
parallel_writes( i, ring, b_len, LFRB_NO_BLOCK );