audioutils: Enhance IpcBuffer API for LL player. [2/3]

PD#SWPL-132311

Problem:
Need aditional API to implement low latency audio
feature.

Solution:
Enhance IpcBuffer API.

Verify:
NTS LLP test

Change-Id: I59eb9b06cbb1ab0008e7be1ae78f1edcd4c89155
Signed-off-by: Tim Yao <tim.yao@amlogic.com>
diff --git a/include/IpcBuffer/IpcBuffer.h b/include/IpcBuffer/IpcBuffer.h
index 96025b0..6ff3fc7 100644
--- a/include/IpcBuffer/IpcBuffer.h
+++ b/include/IpcBuffer/IpcBuffer.h
@@ -1,6 +1,7 @@
 #ifndef __IPCBUFFER_H
 #define __IPCBUFFER_H
 
+#include <time.h>
 #include <boost/interprocess/managed_shared_memory.hpp>
 
 using namespace boost::interprocess;
@@ -19,8 +20,18 @@
   void get_write_position(uint64_t& time, uint64_t& position);
   void reset();
   uint8_t *start_ptr();
+  uint64_t wp() { return wr_position_; }
   const char *name();
 
+  uint32_t getUnderrun() { return underrun_; }
+  void incUnderrun() { underrun_++; }
+
+  void addSilence(size_t count) { silence_inserted_ += count; }
+  size_t getSilenceInserted() { return silence_inserted_; }
+
+  void setMeta(uint64_t meta_64, uint32_t meta_32);
+  void getMeta(struct timespec *ts, uint64_t *meta_64, uint32_t *meta_32);
+
 private:
   // Note: members can be access from different process
   // only keep information which are common to all processes
@@ -29,9 +40,14 @@
   managed_shared_memory::handle_t handle_;
   std::string name_;
   bool blocking_;
-  interprocess_mutex wr_position_mutex_;
+  interprocess_mutex mutex_;
   uint64_t wr_position_;
   uint64_t wr_time_;
+  uint32_t underrun_;
+  size_t silence_inserted_;
+  struct timespec meta_ts_;
+  uint64_t meta_64_;
+  uint32_t meta_32_;
 };
 
 #endif
diff --git a/include/IpcBuffer/IpcBuffer_c.h b/include/IpcBuffer/IpcBuffer_c.h
index 5a7cea3..9250f40 100644
--- a/include/IpcBuffer/IpcBuffer_c.h
+++ b/include/IpcBuffer/IpcBuffer_c.h
@@ -17,6 +17,22 @@
 
 extern uint64_t IpcBuffer_get_wr_pos(const char *name);
 
+extern size_t IpcBuffer_get_capacity(const char *name);
+
+extern void *IpcBuffer_get_by_name(const char *name);
+
+extern void IpcBuffer_set_water_level_byname(const char *name, size_t level);
+
+extern void IpcBuffer_inc_underrun_byname(const char *name);
+
+extern void IpcBuffer_add_silence_byname(const char *name, size_t size);
+
+extern void IpcBuffer_set_water_level(void *instance, size_t level);
+
+extern void IpcBuffer_inc_underrun(void *instance);
+
+extern void IpcBuffer_add_silence(void *instance, size_t size);
+
 #ifdef __cplusplus
 }
 #endif
diff --git a/src/IpcBuffer/IpcBuffer.cpp b/src/IpcBuffer/IpcBuffer.cpp
index d879cf2..6dc7868 100644
--- a/src/IpcBuffer/IpcBuffer.cpp
+++ b/src/IpcBuffer/IpcBuffer.cpp
@@ -20,6 +20,8 @@
   , wr_position_(0)
   , blocking_(false)
   , wr_time_(0)
+  , underrun_(0)
+  , silence_inserted_(0)
 {
   managed_shared_memory *segment = audio_server_shmem::getInstance();
   void *shptr = segment->allocate(capacity);
@@ -98,7 +100,7 @@
     if (end_index_ == capacity_) end_index_ = 0;
   }
 
-  scoped_lock<interprocess_mutex> lock(wr_position_mutex_);
+  scoped_lock<interprocess_mutex> lock(mutex_);
 
   timespec ts;
   clock_gettime(CLOCK_MONOTONIC_RAW, &ts);
@@ -108,7 +110,7 @@
 
 void IpcBuffer::get_write_position(uint64_t& time, uint64_t& position)
 {
-  scoped_lock<interprocess_mutex> lock(wr_position_mutex_);
+  scoped_lock<interprocess_mutex> lock(mutex_);
   time = wr_time_;
   position = wr_position_;
 }
@@ -125,9 +127,27 @@
 
 void IpcBuffer::reset()
 {
+  scoped_lock<interprocess_mutex> lock(mutex_);
   begin_index_ = end_index_ = size_ = wr_position_ = 0;
 }
 
+void IpcBuffer::setMeta(uint64_t meta_64, uint32_t meta_32)
+{
+  scoped_lock<interprocess_mutex> lock(mutex_);
+  clock_gettime(CLOCK_MONOTONIC_RAW, &meta_ts_);
+  meta_64_ = meta_64;
+  meta_32_ = meta_32;
+}
+
+void IpcBuffer::getMeta(struct timespec *meta_ts, uint64_t *meta_64, uint32_t *meta_32)
+{
+  scoped_lock<interprocess_mutex> lock(mutex_);
+  meta_ts->tv_sec = meta_ts_.tv_sec;
+  meta_ts->tv_nsec = meta_ts_.tv_nsec;
+  *meta_64 = meta_64_;
+  *meta_32 = meta_32_;
+}
+
 managed_shared_memory *audio_server_shmem::shm_;
 
 extern "C" {
@@ -176,5 +196,81 @@
   return 0;
 }
 
+size_t IpcBuffer_get_capacity(const char *name)
+{
+  managed_shared_memory *shm = audio_server_shmem::getInstance();
+  IpcBuffer * cb = shm->find<IpcBuffer>(name).first;
+  if (cb) {
+    return cb->capacity();
+  }
+  return 0;
 }
 
+void *IpcBuffer_get_by_name(const char *name)
+{
+  managed_shared_memory *shm = audio_server_shmem::getInstance();
+  return shm->find<IpcBuffer>(name).first;
+}
+
+void IpcBuffer_set_meta_byname(const char *name, uint64_t meta_64, uint32_t meta_32)
+{
+  managed_shared_memory *shm = audio_server_shmem::getInstance();
+  IpcBuffer * cb = shm->find<IpcBuffer>(name).first;
+  if (cb) {
+    cb->setMeta(meta_64, meta_32);
+  }
+}
+
+void IpcBuffer_inc_underrun_byname(const char *name)
+{
+  managed_shared_memory *shm = audio_server_shmem::getInstance();
+  IpcBuffer * cb = shm->find<IpcBuffer>(name).first;
+  if (cb) {
+    cb->incUnderrun();
+  }
+}
+
+void IpcBuffer_add_silence_byname(const char *name, size_t size)
+{
+  managed_shared_memory *shm = audio_server_shmem::getInstance();
+  IpcBuffer * cb = shm->find<IpcBuffer>(name).first;
+  if (cb) {
+    cb->addSilence(size);
+  }
+}
+
+void IpcBuffer_setMeta_byname(const char *name, uint64_t meta_64, uint32_t meta_32)
+{
+  managed_shared_memory *shm = audio_server_shmem::getInstance();
+  IpcBuffer * cb = shm->find<IpcBuffer>(name).first;
+  if (cb) {
+    cb->setMeta(meta_64, meta_32);
+  }
+}
+
+void IpcBuffer_inc_underrun(void *instance)
+{
+  IpcBuffer * cb = (IpcBuffer *)instance;
+  if (cb) {
+    cb->incUnderrun();
+  }
+}
+
+void IpcBuffer_add_silence(void *instance, size_t size)
+{
+  IpcBuffer * cb = (IpcBuffer *)instance;
+  if (cb) {
+    cb->addSilence(size);
+  }
+}
+
+void IpcBuffer_setMeta(void *instance, uint64_t meta_64, uint32_t meta_32)
+{
+  IpcBuffer * cb = (IpcBuffer *)instance;
+  if (cb) {
+    cb->setMeta(meta_64, meta_32);
+  }
+}
+
+
+}