/*
 * Copyright (c) 2017 Cisco and/or its affiliates.
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at:
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
#ifndef SRC_VNET_SESSION_SEGMENT_MANAGER_H_
#define SRC_VNET_SESSION_SEGMENT_MANAGER_H_

#include <vnet/vnet.h>
#include <svm/svm_fifo_segment.h>

#include <vlibmemory/unix_shared_memory_queue.h>
#include <vlibmemory/api.h>
#include <vppinfra/lock.h>

typedef struct _segment_manager_properties
{
  /** Session fifo sizes.  */
  u32 rx_fifo_size;
  u32 tx_fifo_size;

  /** Configured additional segment size */
  u32 add_segment_size;

  /** Flag that indicates if additional segments should be created */
  u8 add_segment;

  /** Use private memory segment instead of shared memory */
  u8 use_private_segment;
} segment_manager_properties_t;

typedef struct _segment_manager
{
  clib_spinlock_t lockp;

  /** segments mapped by this manager */
  u32 *segment_indices;

  /** Owner app index */
  u32 app_index;

  /** Pointer to manager properties. Could be shared among all of
   * an app's segment managers s*/
  segment_manager_properties_t *properties;
} segment_manager_t;

/** Pool of segment managers */
extern segment_manager_t *segment_managers;

always_inline segment_manager_t *
segment_manager_new ()
{
  segment_manager_t *sm;
  pool_get (segment_managers, sm);
  memset (sm, 0, sizeof (*sm));
  return sm;
}

always_inline segment_manager_t *
segment_manager_get (u32 index)
{
  return pool_elt_at_index (segment_managers, index);
}

always_inline segment_manager_t *
segment_manager_get_if_valid (u32 index)
{
  if (pool_is_free_index (segment_managers, index))
    return 0;
  return pool_elt_at_index (segment_managers, index);
}

always_inline u32
segment_manager_index (segment_manager_t * sm)
{
  return sm - segment_managers;
}

int
segment_manager_init (segment_manager_t * sm,
		      segment_manager_properties_t * properties,
		      u32 seg_size);

void segment_manager_get_segment_info (u32 index, u8 ** name, u32 * size);
int
session_manager_add_first_segment (segment_manager_t * sm, u32 segment_size);
int session_manager_add_segment (segment_manager_t * sm);
void segment_manager_del (segment_manager_t * sm);
int
segment_manager_alloc_session_fifos (segment_manager_t * sm,
				     svm_fifo_t ** server_rx_fifo,
				     svm_fifo_t ** server_tx_fifo,
				     u32 * fifo_segment_index);
void
segment_manager_dealloc_fifos (u32 svm_segment_index, svm_fifo_t * rx_fifo,
			       svm_fifo_t * tx_fifo);
unix_shared_memory_queue_t *segment_manager_alloc_queue (segment_manager_t *
							 sm, u32 queue_size);
void segment_manager_dealloc_queue (segment_manager_t * sm,
				    unix_shared_memory_queue_t * q);

#endif /* SRC_VNET_SESSION_SEGMENT_MANAGER_H_ */
/*
 * fd.io coding-style-patch-verification: ON
 *
 * Local Variables:
 * eval: (c-set-style "gnu")
 * End:
 */
