GNUnet  0.10.x
Functions | Variables
gnunet_gst.c File Reference

FIXME. More...

#include "gnunet_gst_def.h"
Include dependency graph for gnunet_gst.c:

Go to the source code of this file.

Functions

void dump_buffer (unsigned n, const unsigned char *buf)
 
void gg_load_configuration (GNUNET_gstData *d)
 
static void write_data (const char *ptr, size_t msg_size)
 
GstFlowReturn on_appsink_new_sample (GstElement *element, GNUNET_gstData *d)
 
void pl_graph (GstElement *pipeline)
 
gboolean gnunet_gst_bus_call (GstBus *bus, GstMessage *msg, gpointer data)
 
void state_changed_cb (GstBus *bus, GstMessage *msg, GNUNET_gstData *d)
 
static void application_cb (GstBus *bus, GstMessage *msg, GNUNET_gstData *data)
 
static void error_cb (GstBus *bus, GstMessage *msg, GNUNET_gstData *data)
 
static void eos_cb (GstBus *bus, GstMessage *msg, GNUNET_gstData *data)
 
void gg_setup_gst_bus (GNUNET_gstData *d)
 
int feed_buffer_to_gst (const char *audio, size_t b_len, GNUNET_gstData *d)
 
GstElement * gst_element_factory_make_debug (gchar *factoryname, gchar *name)
 debug making elements More...
 
void lf (char *msg)
 
static void autoaudiosink_child_added (GstChildProxy *child_proxy, GObject *object, gchar *name, gpointer user_data)
 
static void autoaudiosource_child_added (GstChildProxy *child_proxy, GObject *object, gchar *name, gpointer user_data)
 
GstElement * get_pipeline (GstElement *element)
 
static void decoder_ogg_pad_added (GstElement *element, GstPad *pad, gpointer data)
 
int gnunet_read (GNUNET_gstData *d)
 
static int stdin_receiver (void *cls, const struct GNUNET_MessageHeader *msg)
 Message callback. More...
 
GstBin * get_app (GNUNET_gstData *d, int type)
 
GstBin * get_coder (GNUNET_gstData *d, int type)
 
GstBin * get_audiobin (GNUNET_gstData *d, int type)
 

Variables

static struct GNUNET_CONFIGURATION_Handlecfg
 Our configuration. More...
 

Detailed Description

FIXME.

Author
Hark

Definition in file gnunet_gst.c.

Function Documentation

◆ dump_buffer()

void dump_buffer ( unsigned  n,
const unsigned char *  buf 
)

Definition at line 34 of file gnunet_gst.c.

References end, and p.

Referenced by stdin_receiver().

35 {
36  const unsigned char *p, *end;
37  unsigned i, j;
38 
39  end = buf + n;
40 
41  for (i = 0; ; i += 16)
42  {
43  p = buf + i;
44  for (j = 0; j < 16; j++)
45  {
46  fprintf(stderr, "%02X ", p[j]);
47  if (p + j >= end)
48  goto BREAKOUT;
49  }
50  fprintf(stderr, " ");
51  p = buf + i;
52  for (j = 0; j < 16; j++)
53  {
54  fprintf(stderr, "%c", isprint(p[j]) ? p[j] :
55  '.');
56  if (p + j >= end)
57  goto BREAKOUT;
58  }
59  fprintf(stderr, "\n");
60  }
61 BREAKOUT:
62  return;
63 }
static int end
Set if we are to shutdown all services (including ARM).
Definition: gnunet-arm.c:34
static struct GNUNET_OS_Process * p
Helper process we started.
Definition: gnunet-qr.c:59
static char buf[2048]
Here is the caller graph for this function:

◆ gg_load_configuration()

void gg_load_configuration ( GNUNET_gstData d)

Definition at line 69 of file gnunet_gst.c.

References ALSA, GNUNET_gstData::audiobackend, AUTO, GNUNET_gstData::dropsilence, FAKE, GNUNET_CONFIGURATION_create(), GNUNET_CONFIGURATION_get_value_string(), GNUNET_CONFIGURATION_get_value_yesno(), GNUNET_CONFIGURATION_load(), GNUNET_YES, JACK, GNUNET_gstData::jack_pp_in, GNUNET_gstData::jack_pp_out, GNUNET_gstData::pure_ogg, TEST, and GNUNET_gstData::usertp.

Referenced by main().

70 {
71  char *audiobackend_string;
72 
74  GNUNET_CONFIGURATION_load(cfg, "mediahelper.conf");
75 
76  GNUNET_CONFIGURATION_get_value_string(cfg, "MEDIAHELPER", "JACK_PP_IN", &d->jack_pp_in);
77  GNUNET_CONFIGURATION_get_value_string(cfg, "MEDIAHELPER", "JACK_PP_OUT", &d->jack_pp_out);
78 
79  GNUNET_CONFIGURATION_get_value_string(cfg, "MEDIAHELPER", "AUDIOBACKEND", &audiobackend_string);
80 
81  // printf("abstring: %s \n", audiobackend_string);
82 
83  if (0 == strcasecmp(audiobackend_string, "AUTO"))
84  {
85  d->audiobackend = AUTO;
86  }
87  else if (0 == strcasecmp(audiobackend_string, "JACK"))
88  {
89  d->audiobackend = JACK;
90  }
91  else if (0 == strcasecmp(audiobackend_string, "ALSA"))
92  {
93  d->audiobackend = ALSA;
94  }
95  else if (0 == strcasecmp(audiobackend_string, "FAKE"))
96  {
97  d->audiobackend = FAKE;
98  }
99  else if (0 == strcasecmp(audiobackend_string, "TEST"))
100  {
101  d->audiobackend = TEST;
102  }
103  else
104  {
105  d->audiobackend = AUTO;
106  }
107 
108  if (GNUNET_CONFIGURATION_get_value_yesno(cfg, "MEDIAHELPER", "REMOVESILENCE") == GNUNET_YES)
109  {
110  d->dropsilence = TRUE;
111  }
112  else
113  {
114  d->dropsilence = FALSE;
115  }
116 
117  if (GNUNET_CONFIGURATION_get_value_yesno(cfg, "MEDIAHELPER", "NO_GN_HEADERS") == GNUNET_YES)
118  {
119  d->pure_ogg = TRUE;
120  }
121  else
122  {
123  d->pure_ogg = FALSE;
124  }
125 
126 
127  if (GNUNET_CONFIGURATION_get_value_yesno(cfg, "MEDIAHELPER", "USERTP") == GNUNET_YES)
128  {
129  d->usertp = TRUE;
130  }
131  else
132  {
133  d->usertp = FALSE;
134  }
135 
136 // GNUNET_CONFIGURATION_write(cfg, "mediahelper.conf");
137 }
struct GNUNET_CONFIGURATION_Handle * GNUNET_CONFIGURATION_create(void)
Create a new configuration object.
int GNUNET_CONFIGURATION_load(struct GNUNET_CONFIGURATION_Handle *cfg, const char *filename)
Load configuration.
int GNUNET_CONFIGURATION_get_value_string(const struct GNUNET_CONFIGURATION_Handle *cfg, const char *section, const char *option, char **value)
Get a configuration value that should be a string.
static struct GNUNET_CONFIGURATION_Handle * cfg
Our configuration.
Definition: gnunet_gst.c:30
#define GNUNET_YES
Definition: gnunet_common.h:77
int GNUNET_CONFIGURATION_get_value_yesno(const struct GNUNET_CONFIGURATION_Handle *cfg, const char *section, const char *option)
Get a configuration value that should be in a set of "YES" or "NO".
Here is the call graph for this function:
Here is the caller graph for this function:

◆ write_data()

static void write_data ( const char *  ptr,
size_t  msg_size 
)
static

Definition at line 140 of file gnunet_gst.c.

References GNUNET_ERROR_TYPE_ERROR, GNUNET_log_strerror, and ret.

Referenced by on_appsink_new_sample().

141 {
142  ssize_t ret;
143  size_t off;
144 
145  off = 0;
146  while (off < msg_size)
147  {
148  ret = write(1, &ptr[off], msg_size - off);
149  if (0 >= ret)
150  {
151  if (-1 == ret)
153 // quit (2);
154  }
155  off += ret;
156  }
157 }
static int ret
Final status code.
Definition: gnunet-arm.c:89
#define GNUNET_log_strerror(level, cmd)
Log an error message at log-level &#39;level&#39; that indicates a failure of the command &#39;cmd&#39; with the mess...
Here is the caller graph for this function:

◆ on_appsink_new_sample()

GstFlowReturn on_appsink_new_sample ( GstElement *  element,
GNUNET_gstData d 
)

Definition at line 162 of file gnunet_gst.c.

References GNUNET_gstData::audio_message, GNUNET_memcpy, AudioMessage::header, len, map, GNUNET_gstData::pure_ogg, GNUNET_MessageHeader::size, and write_data().

Referenced by get_app().

163 {
164  //size of message including gnunet header
165  size_t msg_size;
166 
167  GstSample *s;
168  GstBuffer *b;
169  GstMapInfo map;
170 
171 /*
172  const GstStructure *si;
173  char *si_str;
174  GstCaps *s_caps;
175  char *caps_str;
176  */
177 
178  if (gst_app_sink_is_eos(GST_APP_SINK(element)))
179  return GST_FLOW_OK;
180 
181  //pull sample from appsink
182  s = gst_app_sink_pull_sample(GST_APP_SINK(element));
183 
184  if (s == NULL)
185  return GST_FLOW_OK;
186 
187  if (!GST_IS_SAMPLE(s))
188  return GST_FLOW_OK;
189 
190  b = gst_sample_get_buffer(s);
191 
192  GST_WARNING("caps are %" GST_PTR_FORMAT, gst_sample_get_caps(s));
193 
194 
195 
196  gst_buffer_map(b, &map, GST_MAP_READ);
197 
198  size_t len;
199  len = map.size;
200  if (len > UINT16_MAX - sizeof(struct AudioMessage))
201  {
202  // this should never happen?
203  printf("GSTREAMER sample too big! \n");
204  exit(20);
205  len = UINT16_MAX - sizeof(struct AudioMessage);
206  }
207 
208  msg_size = sizeof(struct AudioMessage) + len;
209 
210  // copy the data into audio_message
211  GNUNET_memcpy(((char *)&(d->audio_message)[1]), map.data, len);
212  (d->audio_message)->header.size = htons((uint16_t)msg_size);
213  if (d->pure_ogg)
214  // write the audio_message without the gnunet headers
215  write_data((const char *)&(d->audio_message)[1], len);
216  else
217  write_data((const char *)d->audio_message, msg_size);
218 
219  gst_sample_unref(s);
220  return GST_FLOW_OK;
221 }
struct AudioMessage * audio_message
struct GNUNET_MessageHeader header
Type is GNUNET_MESSAGE_TYPE_CONVERSATION_AUDIO.
Definition: conversation.h:59
#define GNUNET_memcpy(dst, src, n)
Call memcpy() but check for n being 0 first.
uint16_t size
The length of the struct (in bytes, including the length field itself), in big-endian format...
static struct GNUNET_CONTAINER_MultiPeerMap * map
Handle to the map used to store old latency values for peers.
Message to transmit the audio (between client and helpers).
Definition: conversation.h:55
static void write_data(const char *ptr, size_t msg_size)
Definition: gnunet_gst.c:140
uint16_t len
length of data (which is always a uint32_t, but presumably this can be used to specify that fewer byt...
Here is the call graph for this function:
Here is the caller graph for this function:

◆ pl_graph()

void pl_graph ( GstElement *  pipeline)

Definition at line 227 of file gnunet_gst.c.

Referenced by main(), and state_changed_cb().

228 {
229 #ifdef IS_SPEAKER
230  gst_debug_bin_to_dot_file_with_ts(GST_BIN(pipeline), GST_DEBUG_GRAPH_SHOW_ALL, "playback_helper.dot");
231 #endif
232 #ifdef IS_MIC
233  gst_debug_bin_to_dot_file_with_ts(GST_BIN(pipeline), GST_DEBUG_GRAPH_SHOW_ALL, "record_helper.dot");
234 #endif
235 
236 
237  // load_configuration();
238 }
static GstElement * pipeline
Main pipeline.
Here is the caller graph for this function:

◆ gnunet_gst_bus_call()

gboolean gnunet_gst_bus_call ( GstBus *  bus,
GstMessage *  msg,
gpointer  data 
)

Definition at line 243 of file gnunet_gst.c.

References find_typedefs::debug, GNUNET_ERROR_TYPE_DEBUG, GNUNET_ERROR_TYPE_ERROR, GNUNET_ERROR_TYPE_INFO, and GNUNET_log.

244 {
246  "Bus message\n");
247  switch (GST_MESSAGE_TYPE(msg))
248  {
249  case GST_MESSAGE_EOS:
251  "End of stream\n");
252  exit(10);
253  break;
254 
255  case GST_MESSAGE_ERROR:
256  {
257  gchar *debug;
258  GError *error;
259 
260  gst_message_parse_error(msg, &error, &debug);
261  g_free(debug);
262 
264  "Error: %s\n",
265  error->message);
266  g_error_free(error);
267 
268  exit(10);
269  break;
270  }
271 
272  default:
273  break;
274  }
275 
276  return TRUE;
277 }
struct GNUNET_MessageHeader * msg
Definition: 005.c:2
#define GNUNET_log(kind,...)

◆ state_changed_cb()

void state_changed_cb ( GstBus *  bus,
GstMessage *  msg,
GNUNET_gstData d 
)

Definition at line 281 of file gnunet_gst.c.

References GNUNET_gstData::pipeline, and pl_graph().

Referenced by gg_setup_gst_bus().

282 {
283  GstState old_state, new_state, pending_state;
284 
285  gst_message_parse_state_changed(msg, &old_state, &new_state,
286  &pending_state);
287  switch (new_state)
288  {
289  case GST_STATE_READY:
290 // printf("ready.... \n");
291  //pl_graph(GST_ELEMENT(d->pipeline));
292  break;
293 
294  case GST_STATE_PLAYING:
295 
296  //GST_LOG ("caps are %" GST_PTR_FORMAT, caps);
297 
298  // printf("Playing.... \n");
299  pl_graph(GST_ELEMENT(d->pipeline));
300  break;
301 
302  case GST_STATE_VOID_PENDING:
303  // printf("void_pending.... \n");
304  //pl_graph(GST_ELEMENT(d->pipeline));
305  break;
306 
307  case GST_STATE_NULL:
308  // printf("null.... \n");
309  //pl_graph(GST_ELEMENT(d->pipeline));
310  break;
311 
312  case GST_STATE_PAUSED:
313  // printf("paused.... \n");
314  //pl_graph(GST_ELEMENT(d->pipeline));
315  break;
316  }
317 }
void pl_graph(GstElement *pipeline)
Definition: gnunet_gst.c:227
struct GNUNET_MessageHeader * msg
Definition: 005.c:2
GstPipeline * pipeline
Here is the call graph for this function:
Here is the caller graph for this function:

◆ application_cb()

static void application_cb ( GstBus *  bus,
GstMessage *  msg,
GNUNET_gstData data 
)
static

Definition at line 320 of file gnunet_gst.c.

Referenced by gg_setup_gst_bus().

321 {
322  // printf("application cb");
323  return;
324 }
Here is the caller graph for this function:

◆ error_cb()

static void error_cb ( GstBus *  bus,
GstMessage *  msg,
GNUNET_gstData data 
)
static

Definition at line 327 of file gnunet_gst.c.

Referenced by gg_setup_gst_bus(), GNUNET_RECLAIM_get_attributes_start(), and GNUNET_RECLAIM_ticket_iteration_start().

328 {
329  // printf("error cb");
330  return;
331 }
Here is the caller graph for this function:

◆ eos_cb()

static void eos_cb ( GstBus *  bus,
GstMessage *  msg,
GNUNET_gstData data 
)
static

Definition at line 334 of file gnunet_gst.c.

Referenced by gg_setup_gst_bus().

335 {
336  // printf("eos cb");
337  return;
338 }
Here is the caller graph for this function:

◆ gg_setup_gst_bus()

void gg_setup_gst_bus ( GNUNET_gstData d)

Definition at line 341 of file gnunet_gst.c.

References application_cb(), eos_cb(), error_cb(), GNUNET_gstData::pipeline, and state_changed_cb().

Referenced by main().

342 {
343  GstBus *bus;
344 
345  bus = gst_element_get_bus(GST_ELEMENT(d->pipeline));
346  gst_bus_add_signal_watch(bus);
347  g_signal_connect(G_OBJECT(bus), "message::error", (GCallback)error_cb,
348  d);
349  g_signal_connect(G_OBJECT(bus), "message::eos", (GCallback)eos_cb,
350  d);
351  g_signal_connect(G_OBJECT(bus), "message::state-changed",
352  (GCallback)state_changed_cb, d);
353  g_signal_connect(G_OBJECT(bus), "message::application",
354  (GCallback)application_cb, d);
355  g_signal_connect(G_OBJECT(bus), "message::about-to-finish",
356  (GCallback)application_cb, d);
357  gst_object_unref(bus);
358 }
GstPipeline * pipeline
static void error_cb(GstBus *bus, GstMessage *msg, GNUNET_gstData *data)
Definition: gnunet_gst.c:327
void state_changed_cb(GstBus *bus, GstMessage *msg, GNUNET_gstData *d)
Definition: gnunet_gst.c:281
static void eos_cb(GstBus *bus, GstMessage *msg, GNUNET_gstData *data)
Definition: gnunet_gst.c:334
static void application_cb(GstBus *bus, GstMessage *msg, GNUNET_gstData *data)
Definition: gnunet_gst.c:320
Here is the call graph for this function:
Here is the caller graph for this function:

◆ feed_buffer_to_gst()

int feed_buffer_to_gst ( const char *  audio,
size_t  b_len,
GNUNET_gstData d 
)

Definition at line 481 of file gnunet_gst.c.

References GNUNET_gstData::appsrc, GNUNET_ERROR_TYPE_DEBUG, GNUNET_ERROR_TYPE_INFO, GNUNET_ERROR_TYPE_WARNING, GNUNET_log, GNUNET_OK, and GNUNET_SYSERR.

Referenced by gnunet_read(), and stdin_receiver().

482 {
483  GstBuffer *b;
484  gchar *bufspace;
485  GstFlowReturn flow;
486 
488  "Feeding %u bytes to GStreamer\n",
489  (unsigned int)b_len);
490 
491  bufspace = g_memdup(audio, b_len);
492  b = gst_buffer_new_wrapped(bufspace, b_len);
493  if (NULL == b)
494  {
496  "Failed to wrap a buffer\n");
497  g_free(bufspace);
498  return GNUNET_SYSERR;
499  }
500  if (GST_APP_SRC(d->appsrc) == NULL)
501  exit(10);
502  flow = gst_app_src_push_buffer(GST_APP_SRC(d->appsrc), b);
503  /* They all return GNUNET_OK, because currently player stops when
504  * data stops coming. This might need to be changed for the player
505  * to also stop when pipeline breaks.
506  */
507  switch (flow)
508  {
509  case GST_FLOW_OK:
511  "Fed %u bytes to the pipeline\n",
512  (unsigned int)b_len);
513  break;
514 
515  case GST_FLOW_FLUSHING:
516  /* buffer was dropped, because pipeline state is not PAUSED or PLAYING */
518  "Dropped a buffer\n");
519  break;
520 
521  case GST_FLOW_EOS:
522  /* end of stream */
524  "EOS\n");
525  break;
526 
527  default:
529  "Unexpected push result\n");
530  break;
531  }
532  return GNUNET_OK;
533 }
#define GNUNET_OK
Named constants for return values.
Definition: gnunet_common.h:75
GstElement * appsrc
#define GNUNET_SYSERR
Definition: gnunet_common.h:76
#define GNUNET_log(kind,...)
Here is the caller graph for this function:

◆ gst_element_factory_make_debug()

GstElement* gst_element_factory_make_debug ( gchar *  factoryname,
gchar *  name 
)

debug making elements

Definition at line 541 of file gnunet_gst.c.

References gst_element_factory_make.

542 {
543  GstElement *element;
544 
545  element = gst_element_factory_make(factoryname, name);
546 
547  if (element == NULL)
548  {
549  printf("\n Failed to create element - type: %s name: %s \n", factoryname, name);
550  exit(10);
551  return element;
552  }
553  else
554  {
555  return element;
556  }
557 }
#define gst_element_factory_make(element, name)
Definition: gnunet_gst.h:36
const char * name

◆ lf()

void lf ( char *  msg)

Definition at line 571 of file gnunet_gst.c.

Referenced by get_audiobin().

572 {
573  printf("linking elements failed: %s", msg);
574  exit(10);
575 }
struct GNUNET_MessageHeader * msg
Definition: 005.c:2
Here is the caller graph for this function:

◆ autoaudiosink_child_added()

static void autoaudiosink_child_added ( GstChildProxy *  child_proxy,
GObject *  object,
gchar *  name,
gpointer  user_data 
)
static

Definition at line 581 of file gnunet_gst.c.

References BUFFER_TIME, and LATENCY_TIME.

Referenced by get_audiobin().

585 {
586  if (GST_IS_AUDIO_BASE_SRC(object))
587  g_object_set(object,
588  "buffer-time", (gint64)BUFFER_TIME,
589  "latency-time", (gint64)LATENCY_TIME,
590  NULL);
591 }
#define LATENCY_TIME
Min number of microseconds to buffer in audiosink.
#define BUFFER_TIME
Max number of microseconds to buffer in audiosink.
Here is the caller graph for this function:

◆ autoaudiosource_child_added()

static void autoaudiosource_child_added ( GstChildProxy *  child_proxy,
GObject *  object,
gchar *  name,
gpointer  user_data 
)
static

Definition at line 597 of file gnunet_gst.c.

References BUFFER_TIME, and LATENCY_TIME.

Referenced by get_audiobin().

598 {
599  if (GST_IS_AUDIO_BASE_SRC(object))
600  g_object_set(object, "buffer-time", (gint64)BUFFER_TIME, "latency-time", (gint64)LATENCY_TIME, NULL);
601 }
#define LATENCY_TIME
Min number of microseconds to buffer in audiosink.
#define BUFFER_TIME
Max number of microseconds to buffer in audiosink.
Here is the caller graph for this function:

◆ get_pipeline()

GstElement* get_pipeline ( GstElement *  element)

Definition at line 605 of file gnunet_gst.c.

References p.

606 {
607  GstPipeline *p;
608 
609  p = GST_PIPELINE(gst_object_get_parent(GST_OBJECT(element)));
610 
611  return GST_ELEMENT(p);
612 }
static struct GNUNET_OS_Process * p
Helper process we started.
Definition: gnunet-qr.c:59

◆ decoder_ogg_pad_added()

static void decoder_ogg_pad_added ( GstElement *  element,
GstPad *  pad,
gpointer  data 
)
static

Definition at line 615 of file gnunet_gst.c.

References decoder.

Referenced by get_coder().

618 {
619  GstPad *sinkpad;
620  GstElement *decoder = (GstElement *)data;
621 
622  printf("==== ogg pad added callback \n");
623  /* We can now link this pad with the opus-decoder sink pad */
624 // pl_graph(get_pipeline(element));
625  sinkpad = gst_element_get_static_pad(decoder, "sink");
626 
627  gst_pad_link(pad, sinkpad);
628  gst_element_link_many(element, decoder, NULL);
629  gst_object_unref(sinkpad);
630 }
static GstElement * decoder
uint32_t data
The data value.
Here is the caller graph for this function:

◆ gnunet_read()

int gnunet_read ( GNUNET_gstData d)

Definition at line 634 of file gnunet_gst.c.

References _, FAIL, feed_buffer_to_gst(), GNUNET_ERROR_TYPE_DEBUG, GNUNET_ERROR_TYPE_ERROR, GNUNET_log, GNUNET_MST_from_buffer(), GNUNET_NO, MAXLINE, GNUNET_gstData::pure_ogg, ret, and GNUNET_gstData::stdin_mst.

Referenced by main().

635 {
636  char readbuf[MAXLINE];
637  int ret;
638 
639  printf("read \n");
640  ret = read(0, readbuf, sizeof(readbuf));
641  if (0 > ret)
642  {
644  _("Read error from STDIN: %d %s\n"),
645  ret, strerror(errno));
646  return FAIL;
647  }
648  //toff += ret;
650  "Received %d bytes of audio data\n",
651  (int)ret);
652  if (0 == ret)
653  return FAIL;
654  //#ifdef DEBUG_READ_PURE_OGG
655 
656  if (d->pure_ogg)
657  {
658  feed_buffer_to_gst(readbuf, ret, d);
659  }
660  else
661  {
662  //#endif
664  readbuf,
665  ret,
666  GNUNET_NO,
667  GNUNET_NO);
668  }
669  return 0;
670 }
#define GNUNET_NO
Definition: gnunet_common.h:78
static int ret
Final status code.
Definition: gnunet-arm.c:89
#define _(String)
GNU gettext support macro.
Definition: platform.h:181
#define MAXLINE
How much data to read in one go.
int GNUNET_MST_from_buffer(struct GNUNET_MessageStreamTokenizer *mst, const char *buf, size_t size, int purge, int one_shot)
Add incoming data to the receive buffer and call the callback for all complete messages.
Definition: mst.c:113
struct GNUNET_MessageStreamTokenizer * stdin_mst
#define GNUNET_log(kind,...)
int feed_buffer_to_gst(const char *audio, size_t b_len, GNUNET_gstData *d)
Definition: gnunet_gst.c:481
Here is the call graph for this function:
Here is the caller graph for this function:

◆ stdin_receiver()

static int stdin_receiver ( void *  cls,
const struct GNUNET_MessageHeader msg 
)
static

Message callback.

Parameters
msgmessage we received.
Returns
GNUNET_OK on success, GNUNET_NO to stop further processing due to disconnect (no error) GNUNET_SYSERR to stop further processing due to error

Definition at line 681 of file gnunet_gst.c.

References dump_buffer(), feed_buffer_to_gst(), GNUNET_MESSAGE_TYPE_CONVERSATION_AUDIO, GNUNET_OK, AudioMessage::header, and GNUNET_MessageHeader::size.

Referenced by get_app().

683 {
684  struct AudioMessage *audio;
685  size_t b_len;
686 
687  printf("stdin receiver \n ");
688  dump_buffer(sizeof(msg),
689  (const unsigned char *)msg);
690 
691  switch (ntohs(msg->type))
692  {
694  audio = (struct AudioMessage *)msg;
695 
696  b_len = ntohs(audio->header.size) - sizeof(struct AudioMessage);
697  printf("feeding buffer to gst \n ");
698  feed_buffer_to_gst((const char *)&audio[1], b_len, cls);
699  break;
700 
701  default:
702  printf("No audio message: %u \n ", ntohs(msg->type));
703  break;
704  }
705  return GNUNET_OK;
706 }
struct GNUNET_MessageHeader header
Type is GNUNET_MESSAGE_TYPE_CONVERSATION_AUDIO.
Definition: conversation.h:59
#define GNUNET_OK
Named constants for return values.
Definition: gnunet_common.h:75
uint16_t size
The length of the struct (in bytes, including the length field itself), in big-endian format...
uint16_t type
The type of the message (GNUNET_MESSAGE_TYPE_XXXX), in big-endian format.
Message to transmit the audio (between client and helpers).
Definition: conversation.h:55
#define GNUNET_MESSAGE_TYPE_CONVERSATION_AUDIO
Message to transmit the audio between helper and speaker/microphone library.
int feed_buffer_to_gst(const char *audio, size_t b_len, GNUNET_gstData *d)
Definition: gnunet_gst.c:481
void dump_buffer(unsigned n, const unsigned char *buf)
Definition: gnunet_gst.c:34
Here is the call graph for this function:
Here is the caller graph for this function:

◆ get_app()

GstBin* get_app ( GNUNET_gstData d,
int  type 
)

Definition at line 710 of file gnunet_gst.c.

References GNUNET_gstData::appsink, GNUNET_gstData::appsrc, GNUNET_gstData::audio_message, GNUNET_assert, GNUNET_ERROR_TYPE_DEBUG, GNUNET_log, GNUNET_log_setup(), GNUNET_malloc, GNUNET_MESSAGE_TYPE_CONVERSATION_AUDIO, GNUNET_MST_create(), GNUNET_OK, gst_element_factory_make, AudioMessage::header, on_appsink_new_sample(), SINK, SOURCE, GNUNET_gstData::stdin_mst, stdin_receiver(), and GNUNET_MessageHeader::type.

Referenced by main().

711 {
712  GstBin *bin;
713  GstPad *pad, *ghostpad;
714 
715  if (type == SOURCE)
716  {
717  bin = GST_BIN(gst_bin_new("Gnunet appsrc"));
718 
719 
721  GNUNET_log_setup("gnunet-helper-audio-playback",
722  "WARNING",
723  NULL));
724 
726  "Audio playback starts\n");
727  printf(" creating appsrc \n ");
728  //d->audio_message.header.type = htons (GNUNET_MESSAGE_TYPE_CONVERSATION_AUDIO);
729 
730 // d->audio_message = GNUNET_malloc (UINT16_MAX);
731 // d->audio_message = (AudioMessage*)malloc(sizeof(struct AudioMessage));
732 // d->audio_message = GNUNET_malloc(sizeof(struct AudioMessage));
733 
734 
735  //d->audio_message.header.type = htons (GNUNET_MESSAGE_TYPE_CONVERSATION_AUDIO);
736 
737 
739 
740  if (d->stdin_mst == NULL)
741  printf("stdin_mst = NULL");
742 
743  d->appsrc = gst_element_factory_make("appsrc", "appsrc");
744 
745  gst_bin_add_many(bin, d->appsrc, NULL);
746 // gst_element_link_many ( encoder, muxer, NULL);
747 
748  pad = gst_element_get_static_pad(d->appsrc, "src");
749  ghostpad = gst_ghost_pad_new("src", pad);
750  }
751  if (type == SINK)
752  {
753  bin = GST_BIN(gst_bin_new("Gnunet appsink"));
754 
755 
757  GNUNET_log_setup("gnunet-helper-audio-record",
758  "WARNING",
759  NULL));
760 
762  "Audio source starts\n");
763 
764  d->appsink = gst_element_factory_make("appsink", "appsink");
765 
766  // Move this out of here!
767  d->audio_message = GNUNET_malloc(UINT16_MAX);
769  g_object_set(G_OBJECT(d->appsink), "emit-signals", TRUE, "sync", TRUE, NULL);
770 
771  g_signal_connect(d->appsink, "new-sample",
772  G_CALLBACK(on_appsink_new_sample), &d);
773 
774  gst_bin_add_many(bin, d->appsink, NULL);
775 // gst_element_link_many ( encoder, muxer, NULL);
776 
777  pad = gst_element_get_static_pad(d->appsink, "sink");
778  ghostpad = gst_ghost_pad_new("sink", pad);
779  }
780 
781  /* set the bin pads */
782  gst_pad_set_active(ghostpad, TRUE);
783  gst_element_add_pad(GST_ELEMENT(bin), ghostpad);
784 
785  gst_object_unref(pad);
786 
787  return bin;
788 }
struct AudioMessage * audio_message
struct GNUNET_MessageHeader header
Type is GNUNET_MESSAGE_TYPE_CONVERSATION_AUDIO.
Definition: conversation.h:59
#define GNUNET_assert(cond)
Use this for fatal errors that cannot be handled.
#define GNUNET_OK
Named constants for return values.
Definition: gnunet_common.h:75
static int stdin_receiver(void *cls, const struct GNUNET_MessageHeader *msg)
Message callback.
Definition: gnunet_gst.c:681
uint16_t type
The type of the message (GNUNET_MESSAGE_TYPE_XXXX), in big-endian format.
GstFlowReturn on_appsink_new_sample(GstElement *element, GNUNET_gstData *d)
Definition: gnunet_gst.c:162
struct GNUNET_MessageStreamTokenizer * GNUNET_MST_create(GNUNET_MessageTokenizerCallback cb, void *cb_cls)
Create a message stream tokenizer.
Definition: mst.c:84
#define gst_element_factory_make(element, name)
Definition: gnunet_gst.h:36
struct GNUNET_MessageStreamTokenizer * stdin_mst
GstElement * appsrc
#define GNUNET_log(kind,...)
GstElement * appsink
#define GNUNET_MESSAGE_TYPE_CONVERSATION_AUDIO
Message to transmit the audio between helper and speaker/microphone library.
enum GNUNET_TESTBED_UnderlayLinkModelType type
the type of this model
int GNUNET_log_setup(const char *comp, const char *loglevel, const char *logfile)
Setup logging.
#define GNUNET_malloc(size)
Wrapper around malloc.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ get_coder()

GstBin* get_coder ( GNUNET_gstData d,
int  type 
)

Definition at line 791 of file gnunet_gst.c.

References decoder, DECODER, decoder_ogg_pad_added(), demuxer, ENCODER, gst_element_factory_make, INBAND_FEC_MODE, MAX_PAYLOAD_SIZE, OGG_MAX_DELAY, OGG_MAX_PAGE_DELAY, OPUS_FRAME_SIZE, PACKET_LOSS_PERCENTAGE, SAMPLING_RATE, and GNUNET_gstData::usertp.

Referenced by main().

792 {
793  GstBin *bin;
794  GstPad *srcpad, *sinkpad, *srcghostpad, *sinkghostpad;
795  GstCaps *rtpcaps;
796  GstElement *encoder, *muxer, *decoder, *demuxer, *jitterbuffer, *rtpcapsfilter;
797 
798  if (d->usertp == TRUE)
799  {
800  /*
801  * application/x-rtp, media=(string)audio, clock-rate=(int)48000, encoding-name=(string)OPUS, sprop-maxcapturerate=(string)48000, sprop-stereo=(string)0, payload=(int)96, encoding-params=(string)2, ssrc=(uint)630297634, timestamp-offset=(uint)678334141, seqnum-offset=(uint)16938 */
802 /*
803  rtpcaps = gst_caps_new_simple ("application/x-rtp",
804  "media", G_TYPE_STRING, "audio",
805  "clock-rate", G_TYPE_INT, SAMPLING_RATE,
806  "encoding-name", G_TYPE_STRING, "OPUS",
807  "payload", G_TYPE_INT, 96,
808  "sprop-stereo", G_TYPE_STRING, "0",
809  "encoding-params", G_TYPE_STRING, "2",
810  NULL);
811  */
812  rtpcaps = gst_caps_new_simple("application/x-rtp",
813  "media", G_TYPE_STRING, "audio",
814  "clock-rate", G_TYPE_INT, SAMPLING_RATE,
815  "encoding-name", G_TYPE_STRING, "OPUS",
816  "payload", G_TYPE_INT, 96,
817  "sprop-stereo", G_TYPE_STRING, "0",
818  "encoding-params", G_TYPE_STRING, "2",
819  NULL);
820 
821 
822  rtpcapsfilter = gst_element_factory_make("capsfilter", "rtpcapsfilter");
823 
824  g_object_set(G_OBJECT(rtpcapsfilter),
825  "caps", rtpcaps,
826  NULL);
827  gst_caps_unref(rtpcaps);
828  }
829 
830 
831  if (type == ENCODER)
832  {
833  bin = GST_BIN(gst_bin_new("Gnunet audioencoder"));
834 
835  encoder = gst_element_factory_make("opusenc", "opus-encoder");
836  if (d->usertp == TRUE)
837  {
838  muxer = gst_element_factory_make("rtpopuspay", "rtp-payloader");
839  }
840  else
841  {
842  muxer = gst_element_factory_make("oggmux", "ogg-muxer");
843  }
844  g_object_set(G_OBJECT(encoder),
845  /* "bitrate", 64000, */
846  /* "bandwidth", OPUS_BANDWIDTH_FULLBAND, */
847  "inband-fec", INBAND_FEC_MODE,
848  "packet-loss-percentage", PACKET_LOSS_PERCENTAGE,
849  "max-payload-size", MAX_PAYLOAD_SIZE,
850  "audio", TRUE, /* VoIP, not audio */
851  "frame-size", OPUS_FRAME_SIZE,
852  NULL);
853 
854  if (d->usertp != TRUE)
855  {
856  g_object_set(G_OBJECT(muxer),
857  "max-delay", OGG_MAX_DELAY,
858  "max-page-delay", OGG_MAX_PAGE_DELAY,
859  NULL);
860  }
861 
862  gst_bin_add_many(bin, encoder, muxer, NULL);
863  gst_element_link_many(encoder, muxer, NULL);
864  sinkpad = gst_element_get_static_pad(encoder, "sink");
865  sinkghostpad = gst_ghost_pad_new("sink", sinkpad);
866 
867  srcpad = gst_element_get_static_pad(muxer, "src");
868  srcghostpad = gst_ghost_pad_new("src", srcpad);
869  }
870  if (type == DECODER)
871  {
872  bin = GST_BIN(gst_bin_new("Gnunet audiodecoder"));
873 
874  // decoder
875  if (d->usertp == TRUE)
876  {
877  demuxer = gst_element_factory_make("rtpopusdepay", "ogg-demuxer");
878  jitterbuffer = gst_element_factory_make("rtpjitterbuffer", "rtpjitterbuffer");
879  }
880  else
881  {
882  demuxer = gst_element_factory_make("oggdemux", "ogg-demuxer");
883  }
884  decoder = gst_element_factory_make("opusdec", "opus-decoder");
885 
886  if (d->usertp == TRUE)
887  {
888  gst_bin_add_many(bin, rtpcapsfilter, jitterbuffer, demuxer, decoder, NULL);
889  gst_element_link_many(rtpcapsfilter, jitterbuffer, demuxer, decoder, NULL);
890  sinkpad = gst_element_get_static_pad(rtpcapsfilter, "sink");
891  }
892  else
893  {
894  gst_bin_add_many(bin, demuxer, decoder, NULL);
895 
896  g_signal_connect(demuxer,
897  "pad-added",
898  G_CALLBACK(decoder_ogg_pad_added),
899  decoder);
900 
901  sinkpad = gst_element_get_static_pad(demuxer, "sink");
902  }
903  sinkghostpad = gst_ghost_pad_new("sink", sinkpad);
904 
905  srcpad = gst_element_get_static_pad(decoder, "src");
906  srcghostpad = gst_ghost_pad_new("src", srcpad);
907  }
908 
909  // add pads to the bin
910  gst_pad_set_active(sinkghostpad, TRUE);
911  gst_element_add_pad(GST_ELEMENT(bin), sinkghostpad);
912 
913  gst_pad_set_active(srcghostpad, TRUE);
914  gst_element_add_pad(GST_ELEMENT(bin), srcghostpad);
915 
916 
917  return bin;
918 }
#define SAMPLING_RATE
#define OGG_MAX_PAGE_DELAY
Maximum delay for sending out a page, in ns.
#define OGG_MAX_DELAY
Maximum delay in multiplexing streams, in ns.
#define MAX_PAYLOAD_SIZE
Maximal size of a single opus packet.
#define OPUS_FRAME_SIZE
Size of a single frame fed to the encoder, in ms.
#define gst_element_factory_make(element, name)
Definition: gnunet_gst.h:36
#define PACKET_LOSS_PERCENTAGE
Expected packet loss to prepare for, in percents.
static GstElement * demuxer
enum GNUNET_TESTBED_UnderlayLinkModelType type
the type of this model
static void decoder_ogg_pad_added(GstElement *element, GstPad *pad, gpointer data)
Definition: gnunet_gst.c:615
static GstElement * decoder
#define INBAND_FEC_MODE
Set to 1 to enable forward error correction.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ get_audiobin()

GstBin* get_audiobin ( GNUNET_gstData d,
int  type 
)

Definition at line 922 of file gnunet_gst.c.

References ALSA, GNUNET_gstData::audiobackend, AUTO, autoaudiosink_child_added(), autoaudiosource_child_added(), BUFFER_TIME, conv, GNUNET_gstData::dropsilence, FAKE, filter, gst_element_factory_make, JACK, GNUNET_gstData::jack_pp_out, LATENCY_TIME, lf(), OPUS_CHANNELS, queue(), resampler, sink, SINK, source, and TEST.

Referenced by main().

923 {
924  GstBin *bin;
925  GstElement *sink, *source, *queue, *conv, *resampler, *removesilence, *filter;
926  GstPad *pad, *ghostpad;
927  GstCaps *caps;
928 
929  if (type == SINK)
930  {
931  bin = GST_BIN(gst_bin_new("Gnunet audiosink"));
932 
933  /* Create all the elements */
934  if (d->dropsilence == TRUE)
935  {
936  queue = gst_element_factory_make("queue", "queue");
937  removesilence = gst_element_factory_make("removesilence", "removesilence");
938  }
939 
940  conv = gst_element_factory_make("audioconvert", "converter");
941  resampler = gst_element_factory_make("audioresample", "resampler");
942 
943  if (d->audiobackend == AUTO)
944  {
945  sink = gst_element_factory_make("autoaudiosink", "audiosink");
946  g_signal_connect(sink, "child-added", G_CALLBACK(autoaudiosink_child_added), NULL);
947  }
948 
949  if (d->audiobackend == ALSA)
950  {
951  sink = gst_element_factory_make("alsaaudiosink", "audiosink");
952  }
953 
954  if (d->audiobackend == JACK)
955  {
956  sink = gst_element_factory_make("jackaudiosink", "audiosink");
957 
958  g_object_set(G_OBJECT(sink), "client-name", "gnunet", NULL);
959 
960  if (g_object_class_find_property
961  (G_OBJECT_GET_CLASS(sink), "port-pattern"))
962  {
963 // char *portpattern = "system";
964 
965  g_object_set(G_OBJECT(sink), "port-pattern", d->jack_pp_out,
966  NULL);
967  }
968  }
969 
970  if (d->audiobackend == FAKE)
971  {
972  sink = gst_element_factory_make("fakesink", "audiosink");
973  }
974 
975  g_object_set(sink,
976  "buffer-time", (gint64)BUFFER_TIME,
977  "latency-time", (gint64)LATENCY_TIME,
978  NULL);
979 
980  if (d->dropsilence == TRUE)
981  {
982  // Do not remove silence by default
983  g_object_set(removesilence, "remove", FALSE, NULL);
984  g_object_set(queue, "max-size-buffers", 12, NULL);
985  /*
986  g_signal_connect (source,
987  "need-data",
988  G_CALLBACK(appsrc_need_data),
989  NULL);
990 
991  g_signal_connect (source,
992  "enough-data",
993  G_CALLBACK(appsrc_enough_data),
994  NULL);
995  */
996 /*
997  g_signal_connect (queue,
998  "notify::current-level-bytes",
999  G_CALLBACK(queue_current_level),
1000  NULL);
1001 
1002  g_signal_connect (queue,
1003  "underrun",
1004  G_CALLBACK(queue_underrun),
1005  NULL);
1006 
1007  g_signal_connect (queue,
1008  "running",
1009  G_CALLBACK(queue_running),
1010  NULL);
1011 
1012  g_signal_connect (queue,
1013  "overrun",
1014  G_CALLBACK(queue_overrun),
1015  NULL);
1016 
1017  g_signal_connect (queue,
1018  "pushing",
1019  G_CALLBACK(queue_pushing),
1020  NULL);
1021  */
1022  }
1023 
1024 
1025 
1026 
1027 
1028  gst_bin_add_many(bin, conv, resampler, sink, NULL);
1029  gst_element_link_many(conv, resampler, sink, NULL);
1030 
1031  if (d->dropsilence == TRUE)
1032  {
1033  gst_bin_add_many(bin, queue, removesilence, NULL);
1034 
1035  if (!gst_element_link_many(queue, removesilence, conv, NULL))
1036  lf("queue, removesilence, conv ");
1037 
1038  pad = gst_element_get_static_pad(queue, "sink");
1039  }
1040  else
1041  {
1042  pad = gst_element_get_static_pad(conv, "sink");
1043  }
1044 
1045  ghostpad = gst_ghost_pad_new("sink", pad);
1046  }
1047  else
1048  {
1049  // SOURCE
1050 
1051  bin = GST_BIN(gst_bin_new("Gnunet audiosource"));
1052 
1053  // source = gst_element_factory_make("audiotestsrc", "audiotestsrcbla");
1054 
1055  if (d->audiobackend == AUTO)
1056  {
1057  source = gst_element_factory_make("autoaudiosrc", "audiosource");
1058  }
1059  if (d->audiobackend == ALSA)
1060  {
1061  source = gst_element_factory_make("alsasrc", "audiosource");
1062  }
1063  if (d->audiobackend == JACK)
1064  {
1065  source = gst_element_factory_make("jackaudiosrc", "audiosource");
1066  }
1067  if (d->audiobackend == TEST)
1068  {
1069  source = gst_element_factory_make("audiotestsrc", "audiosource");
1070  }
1071 
1072  filter = gst_element_factory_make("capsfilter", "filter");
1073  conv = gst_element_factory_make("audioconvert", "converter");
1074  resampler = gst_element_factory_make("audioresample", "resampler");
1075 
1076  if (d->audiobackend == AUTO)
1077  {
1078  g_signal_connect(source, "child-added", G_CALLBACK(autoaudiosource_child_added), NULL);
1079  }
1080  else
1081  {
1082  if (GST_IS_AUDIO_BASE_SRC(source))
1083  g_object_set(source, "buffer-time", (gint64)BUFFER_TIME, "latency-time", (gint64)LATENCY_TIME, NULL);
1084  if (d->audiobackend == JACK)
1085  {
1086  g_object_set(G_OBJECT(source), "client-name", "gnunet", NULL);
1087  if (g_object_class_find_property
1088  (G_OBJECT_GET_CLASS(source), "port-pattern"))
1089  {
1090  char *portpattern = "moc";
1091 
1092  g_object_set(G_OBJECT(source), "port-pattern", portpattern,
1093  NULL);
1094  }
1095  }
1096  }
1097 
1098  caps = gst_caps_new_simple("audio/x-raw",
1099  /* "format", G_TYPE_STRING, "S16LE", */
1100  /* "rate", G_TYPE_INT, SAMPLING_RATE,*/
1101  "channels", G_TYPE_INT, OPUS_CHANNELS,
1102  /* "layout", G_TYPE_STRING, "interleaved",*/
1103  NULL);
1104 
1105  g_object_set(G_OBJECT(filter),
1106  "caps", caps,
1107  NULL);
1108  gst_caps_unref(caps);
1109 
1110  gst_bin_add_many(bin, source, filter, conv, resampler, NULL);
1111  gst_element_link_many(source, filter, conv, resampler, NULL);
1112 
1113  pad = gst_element_get_static_pad(resampler, "src");
1114 
1115 
1116  /* pads */
1117  ghostpad = gst_ghost_pad_new("src", pad);
1118  }
1119 
1120  /* set the bin pads */
1121  gst_pad_set_active(ghostpad, TRUE);
1122  gst_element_add_pad(GST_ELEMENT(bin), ghostpad);
1123 
1124  gst_object_unref(pad);
1125 
1126  return bin;
1127 }
static void queue(const char *hostname)
Add hostname to the list of requests to be made.
static GstElement * resampler
static GstElement * conv
static void autoaudiosource_child_added(GstChildProxy *child_proxy, GObject *object, gchar *name, gpointer user_data)
Definition: gnunet_gst.c:597
static void autoaudiosink_child_added(GstChildProxy *child_proxy, GObject *object, gchar *name, gpointer user_data)
Definition: gnunet_gst.c:581
static GstElement * sink
static struct GNUNET_CONTAINER_BloomFilter * filter
Bloomfilter to quickly tell if we don&#39;t have the content.
#define gst_element_factory_make(element, name)
Definition: gnunet_gst.h:36
void lf(char *msg)
Definition: gnunet_gst.c:571
static GstElement * source
Appsrc instance into which we write data for the pipeline.
#define LATENCY_TIME
Min number of microseconds to buffer in audiosink.
enum GNUNET_TESTBED_UnderlayLinkModelType type
the type of this model
#define OPUS_CHANNELS
Number of channels.
#define BUFFER_TIME
Max number of microseconds to buffer in audiosink.
Here is the call graph for this function:
Here is the caller graph for this function:

Variable Documentation

◆ cfg

struct GNUNET_CONFIGURATION_Handle* cfg
static

Our configuration.

Definition at line 30 of file gnunet_gst.c.