/* 
 *------------------------------------------------------------------
 * svm.h - shared VM allocation, mmap(...MAP_FIXED...) 
 * brain police
 *
 * Copyright (c) 2009 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 __included_svm_h__
#define __included_svm_h__

#include <pthread.h>
#include <vppinfra/clib.h>
#include <vppinfra/mem.h>

#define MMAP_PAGESIZE (clib_mem_get_page_size())

#define SVM_VERSION ((1<<16) | 1) /* set to declare region ready. */

#define SVM_FLAGS_MHEAP (1<<0)  /* region contains an mheap */
#define SVM_FLAGS_FILE  (1<<1)  /* region backed by one or more files */
#define SVM_FLAGS_NODATA (1<<2)  /* region will be further subdivided */
#define SVM_FLAGS_NEED_DATA_INIT (1<<3) 

#define SVM_PVT_MHEAP_SIZE (128<<10) /* region's private mheap (128k) */

typedef struct svm_region_ {
    volatile uword version;
    pthread_mutex_t mutex;
    pthread_cond_t condvar;
    int mutex_owner_pid;        /* in case of trouble */
    int mutex_owner_tag;       
    uword flags;
    uword virtual_base;         /* base of the region object */
    uword virtual_size;
    void *region_heap;
    void *data_base;            /* data portion base address */
    void *data_heap;            /* data heap, if any */
    volatile void *user_ctx;    /* user context pointer */
    /* stuff allocated in the region's heap */
    uword bitmap_size;          /* nbits in virtual alloc bitmap */
    uword *bitmap;              /* the bitmap */
    char *region_name;
    char *backing_file;
    char **filenames;
    uword *client_pids;
    /* pad */

    /* next page:
     * (64K) clib heap for the region itself
     *
     * data_base -> whatever is in this region
     */

} svm_region_t;

typedef struct svm_map_region_args_ {
    char *root_path;            /* NULL means use the truly global arena */
    char *name;
    uword baseva;
    uword size; 
    uword flags;
    char *backing_file;
    uword backing_mmap_size;
    /* uid, gid to own the svm region(s) */
    int uid;
    int gid;
} svm_map_region_args_t;


/*
 * Memory shared across all router instances. Packet buffers, etc 
 * Base should be "out of the way," and size should be big enough to 
 * cover everything we plan to put here.
 */
#define SVM_GLOBAL_REGION_BASEVA  0x30000000
#define SVM_GLOBAL_REGION_SIZE    (64<<20) 
#define SVM_GLOBAL_REGION_NAME "/global_vm"

/*
 * Memory shared across individual router instances. 
 */
#define SVM_OVERLAY_REGION_BASEVA \
               (SVM_GLOBAL_REGION_BASEVA + SVM_GLOBAL_REGION_SIZE)
#define SVM_OVERLAY_REGION_SIZE   (1<<20) 
#define SVM_OVERLAY_REGION_BASENAME "/overlay_vm"

typedef struct {
    u8 *subregion_name;
} svm_subregion_t;

typedef struct {
    svm_subregion_t *subregions; /* subregion pool */
    uword *name_hash;
    u8 *root_path;
} svm_main_region_t;


void *svm_region_find_or_create (svm_map_region_args_t *a);
void svm_region_init(void);
void svm_region_init_chroot(char *root_path);
void svm_region_init_chroot_uid_gid(char *root_path, int uid, int gid);
void svm_region_exit (void);
void svm_region_unmap(void *rp_arg);
void svm_client_scan (char *root_path);
void svm_client_scan_this_region_nolock (svm_region_t *rp);
u8 *shm_name_from_svm_map_region_args (svm_map_region_args_t *a);

static inline void *svm_mem_alloc (svm_region_t *rp, uword size)
{
    u8 *oldheap;
    ASSERT(rp->flags & SVM_FLAGS_MHEAP);
    u8 *rv;

    pthread_mutex_lock(&rp->mutex);
    oldheap = clib_mem_set_heap(rp->data_heap);
    rv = clib_mem_alloc (size);
    clib_mem_set_heap(oldheap);
    pthread_mutex_unlock(&rp->mutex);
    return (rv);
}

static inline void *svm_mem_alloc_aligned_at_offset (svm_region_t *rp,
                                                     uword size, 
                                                     uword align,
                                                     uword offset)
{
    u8 *oldheap;
    ASSERT(rp->flags & SVM_FLAGS_MHEAP);
    u8 *rv;

    pthread_mutex_lock(&rp->mutex);
    oldheap = clib_mem_set_heap(rp->data_heap);
    rv = clib_mem_alloc_aligned_at_offset (size, align, offset);
    clib_mem_set_heap(oldheap);
    pthread_mutex_unlock(&rp->mutex);
    return (rv);
}

static inline void svm_mem_free (svm_region_t *rp, void *ptr)
{
    u8 *oldheap;
    ASSERT(rp->flags & SVM_FLAGS_MHEAP);

    pthread_mutex_lock(&rp->mutex);
    oldheap = clib_mem_set_heap(rp->data_heap);
    clib_mem_free (ptr);
    clib_mem_set_heap(oldheap);
    pthread_mutex_unlock(&rp->mutex);

}

static inline void *svm_push_pvt_heap (svm_region_t *rp)
{
    u8 *oldheap;
    oldheap = clib_mem_set_heap(rp->region_heap);
    return ((void *) oldheap);
}

static inline void *svm_push_data_heap (svm_region_t *rp)
{
    u8 *oldheap;
    oldheap = clib_mem_set_heap(rp->data_heap);
    return ((void *) oldheap);
}

static inline void svm_pop_heap (void *oldheap)
{
    clib_mem_set_heap(oldheap);
}

u8 * format_svm_region (u8 * s, va_list * args);

svm_region_t *svm_get_root_rp (void);

#endif /* __included_svm_h__ */
