File: vringbuffer.h

package info (click to toggle)
jack-capture 0.9.73-3
  • links: PTS, VCS
  • area: main
  • in suites: bookworm, bullseye, buster
  • size: 484 kB
  • ctags: 800
  • sloc: ansic: 4,538; cpp: 1,774; makefile: 133; sh: 119
file content (128 lines) | stat: -rw-r--r-- 3,948 bytes parent folder | download | duplicates (2)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128

#include <stdbool.h>

#include <unistd.h>

#include <pthread.h>

#ifdef __APPLE__
#include <mach/mach.h>
#else
#include <semaphore.h>
#endif

#include "upwaker.h"


#include <jack/ringbuffer.h>

enum vringbuffer_receiver_callback_return_t {
  VRB_CALLBACK_DIDNT_USE_BUFFER,
  VRB_CALLBACK_USED_BUFFER
};

struct vringbuffer_t;

typedef  int (*Vringbuffer_autoincrease_callback) (struct vringbuffer_t *vrb, bool first_time, int reading_size, int writing_size);
typedef  enum vringbuffer_receiver_callback_return_t (*Vringbuffer_receiver_callback) (struct vringbuffer_t *vrb, bool first_time, void *buffer);

typedef struct vringbuffer_list_t{
  struct vringbuffer_list_t *next;
}vringbuffer_list_t;


typedef struct vringbuffer_t{
  jack_ringbuffer_t *for_writer1;
  jack_ringbuffer_t *for_writer2;
  jack_ringbuffer_t *for_reader;

  size_t element_size;

  int curr_num_elements;
  int max_num_elements;
  vringbuffer_list_t *allocated_mem;

  pthread_mutex_t increase_lock;

  bool please_stop;

  // Receiver callback
  pthread_t receiver_thread;
  upwaker_t *receiver_trigger;
#ifdef __APPLE__
  semaphore_t receiver_started;
#else
  sem_t receiver_started;
#endif
  Vringbuffer_receiver_callback receiver_callback;

  // Autoincrease callback
  pthread_t autoincrease_thread;
  upwaker_t *autoincrease_trigger;
#ifdef __APPLE__
  semaphore_t autoincrease_started;
#else
  sem_t autoincrease_started;
#endif
  Vringbuffer_autoincrease_callback autoincrease_callback;
  useconds_t autoincrease_interval;
}vringbuffer_t;




vringbuffer_t* vringbuffer_create	(int num_elements_during_startup, int max_num_elements,size_t element_size);
void vringbuffer_stop_callbacks(vringbuffer_t* vrb);
void vringbuffer_delete(vringbuffer_t* vrb);

void	vringbuffer_increase		(vringbuffer_t *vrb, int num_elements, void **elements);

// Creates a new autoincrease thread. The callback is called each 'interval' microseconds.
// The callback does not have to allocate memory itself, but instead the function returns the number of elements (not bytes) to allocate.
// The callback is also responsible for setting nicety and priority of the thread. This should be done when called the first time (i.e. when first_time==true).
//
// The return value for autoincrease_callback is also ignored the first time, and both reading_size and writing_size will have the values 0.
// Furthermore, the first time autoincrease_callback is called, it is called before vringbuffer_set_autoincrease_callback() returns
//
// An autoincrease callback could be implemented like this:
/*
  static int autoincrease_callback(vringbuffer_t *vrb, bool first_call, size_t reading_size, size_t writing_size){
     if(first_call){
       set_high_priority();
       return 0;
     }
     if(writing_size < 1024)
       return 2;
     return 0;
  }

  int main(){
    ...
    vringbuffer_t *vrg = vrngbuffer_create(quite_large_number,very_large_number,element_size);
    vringbuffer_set_autoincrease_callback(vrg,autoincrease_callback,quite_often);
    ...
  }
*/

// Set interval==0 if you wan't the callback to be triggered if using the trigger_autoincrease_callback function.
void    vringbuffer_set_autoincrease_callback  (vringbuffer_t *vrg, Vringbuffer_autoincrease_callback callback, useconds_t interval);

// Don't call unless interval==0
void vringbuffer_trigger_autoincrease_callback(vringbuffer_t *vrb);

void*	vringbuffer_get_reading		(vringbuffer_t *vrb);
void    vringbuffer_return_reading	(vringbuffer_t *vrb, void *data);
// Returns available number of elements in the ringbuffer
int	vringbuffer_reading_size	(vringbuffer_t *vrb);

void vringbuffer_set_receiver_callback(vringbuffer_t *vrb,Vringbuffer_receiver_callback receiver_callback);

void*	vringbuffer_get_writing		(vringbuffer_t *vrb);
void	vringbuffer_return_writing	(vringbuffer_t *vrb, void *data);
// Returns available number of elements in the ringbuffer
int	vringbuffer_writing_size	(vringbuffer_t *vrb);