Add a new ring_buffer class
This commit was SVN r22615.
Этот коммит содержится в:
родитель
58a1151566
Коммит
7a1b2a706e
@ -29,7 +29,8 @@ headers += \
|
||||
class/opal_graph.h\
|
||||
class/opal_atomic_lifo.h \
|
||||
class/opal_pointer_array.h \
|
||||
class/opal_value_array.h
|
||||
class/opal_value_array.h \
|
||||
class/opal_ring_buffer.h
|
||||
|
||||
libopen_pal_la_SOURCES += \
|
||||
class/opal_bitmap.c \
|
||||
@ -40,4 +41,6 @@ libopen_pal_la_SOURCES += \
|
||||
class/opal_graph.c\
|
||||
class/opal_atomic_lifo.c \
|
||||
class/opal_pointer_array.c \
|
||||
class/opal_value_array.c
|
||||
class/opal_value_array.c \
|
||||
class/opal_ring_buffer.c
|
||||
|
||||
|
85
opal/class/opal_ring_buffer.c
Обычный файл
85
opal/class/opal_ring_buffer.c
Обычный файл
@ -0,0 +1,85 @@
|
||||
/* -*- Mode: C; c-basic-offset:4 ; -*- */
|
||||
/*
|
||||
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
|
||||
* University Research and Technology
|
||||
* Corporation. All rights reserved.
|
||||
* Copyright (c) 2004-2007 The University of Tennessee and The University
|
||||
* of Tennessee Research Foundation. All rights
|
||||
* reserved.
|
||||
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
|
||||
* University of Stuttgart. All rights reserved.
|
||||
* Copyright (c) 2004-2005 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 2010 Cisco Systems, Inc. All rights reserved.
|
||||
* $COPYRIGHT$
|
||||
*
|
||||
* Additional copyrights may follow
|
||||
*
|
||||
* $HEADER$
|
||||
*/
|
||||
|
||||
#include "opal_config.h"
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <assert.h>
|
||||
|
||||
#include "opal/constants.h"
|
||||
#include "opal/class/opal_ring_buffer.h"
|
||||
#include "opal/util/output.h"
|
||||
|
||||
static void opal_ring_buffer_construct(opal_ring_buffer_t *);
|
||||
static void opal_ring_buffer_destruct(opal_ring_buffer_t *);
|
||||
|
||||
OBJ_CLASS_INSTANCE(opal_ring_buffer_t, opal_object_t,
|
||||
opal_ring_buffer_construct,
|
||||
opal_ring_buffer_destruct);
|
||||
|
||||
/*
|
||||
* opal_ring_buffer constructor
|
||||
*/
|
||||
static void opal_ring_buffer_construct(opal_ring_buffer_t *ring)
|
||||
{
|
||||
OBJ_CONSTRUCT(&ring->lock, opal_mutex_t);
|
||||
ring->head = NULL;
|
||||
ring->tail = NULL;
|
||||
ring->size = 0;
|
||||
ring->addr = NULL;
|
||||
}
|
||||
|
||||
/*
|
||||
* opal_ring_buffer destructor
|
||||
*/
|
||||
static void opal_ring_buffer_destruct(opal_ring_buffer_t *ring)
|
||||
{
|
||||
if( NULL != ring->addr) {
|
||||
free(ring->addr);
|
||||
ring->addr = NULL;
|
||||
}
|
||||
|
||||
ring->size = 0;
|
||||
|
||||
OBJ_DESTRUCT(&ring->lock);
|
||||
}
|
||||
|
||||
/**
|
||||
* initialize a ring object
|
||||
*/
|
||||
int opal_ring_buffer_init(opal_ring_buffer_t* ring, int size)
|
||||
{
|
||||
/* check for errors */
|
||||
if (NULL == ring) {
|
||||
return OPAL_ERR_BAD_PARAM;
|
||||
}
|
||||
|
||||
/* Allocate and set the ring to NULL */
|
||||
ring->addr = (char **)calloc(size * sizeof(char*), 1);
|
||||
if (NULL == ring->addr) { /* out of memory */
|
||||
return OPAL_ERR_OUT_OF_RESOURCE;
|
||||
}
|
||||
ring->size = size;
|
||||
/* point the head to the first location */
|
||||
ring->head = &ring->addr[0];
|
||||
|
||||
return OPAL_SUCCESS;
|
||||
}
|
139
opal/class/opal_ring_buffer.h
Обычный файл
139
opal/class/opal_ring_buffer.h
Обычный файл
@ -0,0 +1,139 @@
|
||||
/* -*- Mode: C; c-basic-offset:4 ; -*- */
|
||||
/*
|
||||
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
|
||||
* University Research and Technology
|
||||
* Corporation. All rights reserved.
|
||||
* Copyright (c) 2004-2008 The University of Tennessee and The University
|
||||
* of Tennessee Research Foundation. All rights
|
||||
* reserved.
|
||||
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
|
||||
* University of Stuttgart. All rights reserved.
|
||||
* Copyright (c) 2004-2005 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 2010 Cisco Systems, Inc. All rights reserved.
|
||||
* $COPYRIGHT$
|
||||
*
|
||||
* Additional copyrights may follow
|
||||
*
|
||||
* $HEADER$
|
||||
*/
|
||||
/** @file
|
||||
*
|
||||
*/
|
||||
|
||||
#ifndef OPAL_RING_BUFFER_H
|
||||
#define OPAL_RING_BUFFER_H
|
||||
|
||||
#include "opal_config.h"
|
||||
|
||||
#include "opal/threads/mutex.h"
|
||||
#include "opal/class/opal_object.h"
|
||||
#include "opal/util/output.h"
|
||||
|
||||
BEGIN_C_DECLS
|
||||
|
||||
/**
|
||||
* dynamic pointer ring
|
||||
*/
|
||||
struct opal_ring_buffer_t {
|
||||
/** base class */
|
||||
opal_object_t super;
|
||||
/** synchronization object */
|
||||
opal_mutex_t lock;
|
||||
/* head/tail indices */
|
||||
char **head;
|
||||
char **tail;
|
||||
/** size of list, i.e. number of elements in addr */
|
||||
int size;
|
||||
/** pointer to ring */
|
||||
char **addr;
|
||||
};
|
||||
/**
|
||||
* Convenience typedef
|
||||
*/
|
||||
typedef struct opal_ring_buffer_t opal_ring_buffer_t;
|
||||
/**
|
||||
* Class declaration
|
||||
*/
|
||||
OPAL_DECLSPEC OBJ_CLASS_DECLARATION(opal_ring_buffer_t);
|
||||
|
||||
/**
|
||||
* Initialize the ring buffer, defining its size.
|
||||
*
|
||||
* @param ring Pointer to a ring buffer (IN/OUT)
|
||||
* @param size The number of elements in the ring (IN)
|
||||
*
|
||||
* @return OPAL_SUCCESS if all initializations were succesful. Otherwise,
|
||||
* the error indicate what went wrong in the function.
|
||||
*/
|
||||
OPAL_DECLSPEC int opal_ring_buffer_init(opal_ring_buffer_t* ring, int size);
|
||||
|
||||
/**
|
||||
* Push an item onto the ring buffer
|
||||
*
|
||||
* @param ring Pointer to ring (IN)
|
||||
* @param ptr Pointer value (IN)
|
||||
*
|
||||
* @return OPAL_SUCCESS. Returns error if ring cannot take
|
||||
* another entry
|
||||
*/
|
||||
static inline void* opal_ring_buffer_push(opal_ring_buffer_t *ring, void *ptr)
|
||||
{
|
||||
char *p=NULL;
|
||||
|
||||
OPAL_THREAD_LOCK(&(ring->lock));
|
||||
if (NULL != *ring->head) {
|
||||
p = *ring->head;
|
||||
if (ring->head == ring->tail) {
|
||||
/* push the tail ahead of us */
|
||||
if (ring->tail == &ring->addr[ring->size-1]) {
|
||||
ring->tail = &ring->addr[0];
|
||||
} else {
|
||||
ring->tail++;
|
||||
}
|
||||
}
|
||||
}
|
||||
*ring->head = ptr;
|
||||
if (ring->head == &ring->addr[ring->size-1]) {
|
||||
ring->head = &ring->addr[0];
|
||||
} else {
|
||||
ring->head++;
|
||||
}
|
||||
OPAL_THREAD_UNLOCK(&(ring->lock));
|
||||
return (void*)p;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Pop an item off of the ring. The head of the ring will be
|
||||
* returned. If nothing on the ring, NULL is returned.
|
||||
*
|
||||
* @param ring Pointer to ring (IN)
|
||||
*
|
||||
* @return Error code. NULL indicates an error.
|
||||
*/
|
||||
|
||||
static inline void* opal_ring_buffer_pop(opal_ring_buffer_t *ring)
|
||||
{
|
||||
char *p;
|
||||
|
||||
OPAL_THREAD_LOCK(&(ring->lock));
|
||||
if (NULL == ring->tail || ring->head == ring->tail) {
|
||||
p = NULL;
|
||||
} else {
|
||||
p = *ring->tail;
|
||||
*ring->tail = NULL;
|
||||
if (ring->tail == &ring->addr[ring->size-1]) {
|
||||
ring->tail = &ring->addr[0];
|
||||
} else {
|
||||
ring->tail++;
|
||||
}
|
||||
}
|
||||
OPAL_THREAD_UNLOCK(&(ring->lock));
|
||||
return (void*)p;
|
||||
}
|
||||
|
||||
|
||||
END_C_DECLS
|
||||
|
||||
#endif /* OPAL_RING_BUFFER_H */
|
Загрузка…
x
Ссылка в новой задаче
Block a user