/* * Copyright (c) 2016 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_vppjni_h__ #define __included_vppjni_h__ #include #include #include #include #include #include typedef struct { /* Unique identifier used for matching replays with requests */ volatile u32 context_id; /* Spinlock */ volatile u32 lock; u32 tag; /* Used for first control ping */ // TODO better names? volatile u32 result_ready; volatile i32 retval; /* JNI Native Method Interface pointer for message handlers */ JNIEnv *jenv; /* thread cleanup */ pthread_key_t cleanup_rx_thread_key; /* JNI Invoke Interface pointer for attachment of rx thread to java thread */ JavaVM *jvm; /* Callback object and class references enabling asynchronous Java calls */ jobject callback; jclass callbackClass; /* Connected indication */ volatile u8 is_connected; /* Convenience */ unix_shared_memory_queue_t * vl_input_queue; u32 my_client_index; } vppjni_main_t; vppjni_main_t vppjni_main __attribute__((aligned (64))); static inline u32 vppjni_get_context_id (vppjni_main_t * jm) { return __sync_add_and_fetch (&jm->context_id, 1); } static inline void vppjni_lock (vppjni_main_t * jm, u32 tag) { while (__sync_lock_test_and_set (&jm->lock, 1)) ; jm->tag = tag; } static inline void vppjni_unlock (vppjni_main_t * jm) { jm->tag = 0; CLIB_MEMORY_BARRIER(); jm->lock = 0; } static inline int vppjni_sanity_check (vppjni_main_t * jm) { if (!jm->is_connected) return VNET_API_ERROR_NOT_CONNECTED; return 0; } // TODO remove macros (code is now fully autogenerated) /* M: construct, but don't yet send a message */ #define M(T,t) \ do { \ jm->result_ready = 0; \ mp = vl_msg_api_alloc(sizeof(*mp)); \ memset (mp, 0, sizeof (*mp)); \ mp->_vl_msg_id = ntohs (VL_API_##T); \ mp->client_index = jm->my_client_index; \ } while(0); #define M2(T,t,n) \ do { \ jm->result_ready = 0; \ mp = vl_msg_api_alloc(sizeof(*mp)+(n)); \ memset (mp, 0, sizeof (*mp)); \ mp->_vl_msg_id = ntohs (VL_API_##T); \ mp->client_index = jm->my_client_index; \ } while(0); /* S: send a message */ #define S (vl_msg_api_send_shmem (jm->vl_input_queue, (u8 *)&mp)) #endif /* __included_vppjni_h__ */