summaryrefslogtreecommitdiffstats
path: root/vpp-api/java/jvpp/gen/jvppgen/jvpp_c_gen.py
diff options
context:
space:
mode:
Diffstat (limited to 'vpp-api/java/jvpp/gen/jvppgen/jvpp_c_gen.py')
-rw-r--r--vpp-api/java/jvpp/gen/jvppgen/jvpp_c_gen.py343
1 files changed, 0 insertions, 343 deletions
diff --git a/vpp-api/java/jvpp/gen/jvppgen/jvpp_c_gen.py b/vpp-api/java/jvpp/gen/jvppgen/jvpp_c_gen.py
deleted file mode 100644
index 5fc84c7b050..00000000000
--- a/vpp-api/java/jvpp/gen/jvppgen/jvpp_c_gen.py
+++ /dev/null
@@ -1,343 +0,0 @@
-#!/usr/bin/env python
-#
-# 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
-# l
-# 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.
-#
-
-import os, util
-from string import Template
-
-import jni_gen
-
-
-def is_manually_generated(f_name, plugin_name):
- return f_name in {'control_ping_reply'}
-
-
-class_reference_template = Template("""jclass ${ref_name}Class;
-""")
-
-find_class_invocation_template = Template("""
- ${ref_name}Class = (jclass)(*env)->NewGlobalRef(env, (*env)->FindClass(env, "io/fd/vpp/jvpp/${plugin_name}/dto/${class_name}"));
- if ((*env)->ExceptionCheck(env)) {
- (*env)->ExceptionDescribe(env);
- return JNI_ERR;
- }""")
-
-find_class_template = Template("""
- ${ref_name}Class = (jclass)(*env)->NewGlobalRef(env, (*env)->FindClass(env, "${class_name}"));
- if ((*env)->ExceptionCheck(env)) {
- (*env)->ExceptionDescribe(env);
- return JNI_ERR;
- }""")
-
-delete_class_invocation_template = Template("""
- if (${ref_name}Class) {
- (*env)->DeleteGlobalRef(env, ${ref_name}Class);
- }""")
-
-class_cache_template = Template("""
-$class_references
-static int cache_class_references(JNIEnv* env) {
- $find_class_invocations
- return 0;
-}
-
-static void delete_class_references(JNIEnv* env) {
- $delete_class_invocations
-}""")
-
-
-def generate_class_cache(func_list, plugin_name):
- class_references = []
- find_class_invocations = []
- delete_class_invocations = []
- for f in func_list:
- c_name = f['name']
- class_name = util.underscore_to_camelcase_upper(c_name)
- ref_name = util.underscore_to_camelcase(c_name)
-
- if util.is_ignored(c_name) or util.is_control_ping(class_name):
- continue
-
- if util.is_reply(class_name):
- class_references.append(class_reference_template.substitute(
- ref_name=ref_name))
- find_class_invocations.append(find_class_invocation_template.substitute(
- plugin_name=plugin_name,
- ref_name=ref_name,
- class_name=class_name))
- delete_class_invocations.append(delete_class_invocation_template.substitute(ref_name=ref_name))
- elif util.is_notification(c_name):
- class_references.append(class_reference_template.substitute(
- ref_name=util.add_notification_suffix(ref_name)))
- find_class_invocations.append(find_class_invocation_template.substitute(
- plugin_name=plugin_name,
- ref_name=util.add_notification_suffix(ref_name),
- class_name=util.add_notification_suffix(class_name)))
- delete_class_invocations.append(delete_class_invocation_template.substitute(
- ref_name=util.add_notification_suffix(ref_name)))
-
- # add exception class to class cache
- ref_name = 'callbackException'
- class_name = 'io/fd/vpp/jvpp/VppCallbackException'
- class_references.append(class_reference_template.substitute(
- ref_name=ref_name))
- find_class_invocations.append(find_class_template.substitute(
- ref_name=ref_name,
- class_name=class_name))
- delete_class_invocations.append(delete_class_invocation_template.substitute(ref_name=ref_name))
-
- return class_cache_template.substitute(
- class_references="".join(class_references), find_class_invocations="".join(find_class_invocations),
- delete_class_invocations="".join(delete_class_invocations))
-
-
-# TODO: cache method and field identifiers to achieve better performance
-# https://jira.fd.io/browse/HONEYCOMB-42
-request_class_template = Template("""
- jclass requestClass = (*env)->FindClass(env, "io/fd/vpp/jvpp/${plugin_name}/dto/${java_name_upper}");""")
-
-request_field_identifier_template = Template("""
- jfieldID ${field_reference_name}FieldId = (*env)->GetFieldID(env, ${object_name}Class, "${field_name}", "${jni_signature}");
- ${jni_type} ${field_reference_name} = (*env)->Get${jni_getter}(env, ${object_name}, ${field_reference_name}FieldId);
- """)
-
-
-jni_impl_template = Template("""
-/**
- * JNI binding for sending ${c_name} message.
- * Generated based on $inputfile preparsed data:
-$api_data
- */
-JNIEXPORT jint JNICALL Java_io_fd_vpp_jvpp_${plugin_name}_JVpp${java_plugin_name}Impl_${field_name}0
-(JNIEnv * env, jclass clazz$args) {
- ${plugin_name}_main_t *plugin_main = &${plugin_name}_main;
- vl_api_${c_name}_t * mp;
- u32 my_context_id = vppjni_get_context_id (&jvpp_main);
- $request_class
-
- // create message:
- mp = vl_msg_api_alloc(sizeof(*mp));
- memset (mp, 0, sizeof (*mp));
- mp->_vl_msg_id = ntohs (VL_API_${c_name_uppercase} + plugin_main->msg_id_base);
- mp->client_index = plugin_main->my_client_index;
- mp->context = clib_host_to_net_u32 (my_context_id);
-
- $msg_initialization
-
- // send message:
- vl_msg_api_send_shmem (plugin_main->vl_input_queue, (u8 *)&mp);
- if ((*env)->ExceptionCheck(env)) {
- return JNI_ERR;
- }
- return my_context_id;
-}""")
-
-def generate_jni_impl(func_list, plugin_name, inputfile):
- jni_impl = []
- for f in func_list:
- f_name = f['name']
- camel_case_function_name = util.underscore_to_camelcase(f_name)
- if is_manually_generated(f_name, plugin_name) or util.is_reply(camel_case_function_name) \
- or util.is_ignored(f_name) or util.is_just_notification(f_name):
- continue
-
- arguments = ''
- request_class = ''
- msg_initialization = ''
- f_name_uppercase = f_name.upper()
-
- if f['args']:
- arguments = ', jobject request'
- camel_case_function_name_upper = util.underscore_to_camelcase_upper(f_name)
-
- request_class = request_class_template.substitute(
- java_name_upper=camel_case_function_name_upper,
- plugin_name=plugin_name)
-
- for t in zip(f['types'], f['args'], f['lengths']):
- field_name = util.underscore_to_camelcase(t[1])
- msg_initialization += jni_gen.jni_request_binding_for_type(field_type=t[0], c_name=t[1],
- field_reference_name=field_name,
- field_name=field_name,
- field_length=t[2][0],
- is_variable_len_array=t[2][1])
-
- jni_impl.append(jni_impl_template.substitute(
- inputfile=inputfile,
- api_data=util.api_message_to_javadoc(f),
- field_reference_name=camel_case_function_name,
- field_name=camel_case_function_name,
- c_name_uppercase=f_name_uppercase,
- c_name=f_name,
- plugin_name=plugin_name,
- java_plugin_name=plugin_name.title(),
- request_class=request_class,
- msg_initialization=msg_initialization,
- args=arguments))
-
- return "\n".join(jni_impl)
-
-# code fragment for checking result of the operation before sending request reply
-callback_err_handler_template = Template("""
- // for negative result don't send callback message but send error callback
- if (mp->retval<0) {
- call_on_error("${handler_name}", mp->context, mp->retval, plugin_main->callbackClass, plugin_main->callbackObject, callbackExceptionClass);
- return;
- }
- if (mp->retval == VNET_API_ERROR_IN_PROGRESS) {
- clib_warning("Result in progress");
- return;
- }
-""")
-
-msg_handler_template = Template("""
-/**
- * Handler for ${handler_name} message.
- * Generated based on $inputfile preparsed data:
-$api_data
- */
-static void vl_api_${handler_name}_t_handler (vl_api_${handler_name}_t * mp)
-{
- ${plugin_name}_main_t *plugin_main = &${plugin_name}_main;
- JNIEnv *env = jvpp_main.jenv;
-
- $err_handler
-
- jmethodID constructor = (*env)->GetMethodID(env, ${class_ref_name}Class, "<init>", "()V");
- jmethodID callbackMethod = (*env)->GetMethodID(env, plugin_main->callbackClass, "on${dto_name}", "(Lio/fd/vpp/jvpp/${plugin_name}/dto/${dto_name};)V");
-
- jobject dto = (*env)->NewObject(env, ${class_ref_name}Class, constructor);
- $dto_setters
-
- (*env)->CallVoidMethod(env, plugin_main->callbackObject, callbackMethod, dto);
- // free DTO as per http://stackoverflow.com/questions/1340938/memory-leak-when-calling-java-code-from-c-using-jni
- (*env)->DeleteLocalRef(env, dto);
-}""")
-
-
-def generate_msg_handlers(func_list, plugin_name, inputfile):
- handlers = []
- for f in func_list:
- handler_name = f['name']
- dto_name = util.underscore_to_camelcase_upper(handler_name)
- ref_name = util.underscore_to_camelcase(handler_name)
-
- if is_manually_generated(handler_name, plugin_name) or util.is_ignored(handler_name):
- continue
-
- if not util.is_reply(dto_name) and not util.is_notification(handler_name):
- continue
-
- if util.is_notification(handler_name):
- dto_name = util.add_notification_suffix(dto_name)
- ref_name = util.add_notification_suffix(ref_name)
-
- dto_setters = ''
- err_handler = ''
- # dto setters
- for t in zip(f['types'], f['args'], f['lengths']):
- c_name = t[1]
- java_name = util.underscore_to_camelcase(c_name)
- field_length = t[2][0]
- is_variable_len_array = t[2][1]
- length_field_type = None
- if is_variable_len_array:
- length_field_type = f['types'][f['args'].index(field_length)]
- dto_setters += jni_gen.jni_reply_handler_for_type(handler_name=handler_name, ref_name=ref_name,
- field_type=t[0], c_name=t[1],
- field_reference_name=java_name,
- field_name=java_name, field_length=field_length,
- is_variable_len_array=is_variable_len_array,
- length_field_type=length_field_type)
-
- # for retval don't generate setters and generate retval check
- if util.is_retval_field(c_name):
- err_handler = callback_err_handler_template.substitute(
- handler_name=handler_name
- )
- continue
-
- handlers.append(msg_handler_template.substitute(
- inputfile=inputfile,
- api_data=util.api_message_to_javadoc(f),
- handler_name=handler_name,
- plugin_name=plugin_name,
- dto_name=dto_name,
- class_ref_name=ref_name,
- dto_setters=dto_setters,
- err_handler=err_handler))
-
- return "\n".join(handlers)
-
-
-handler_registration_template = Template("""_(${upercase_name}, ${name}) \\
-""")
-
-
-def generate_handler_registration(func_list):
- handler_registration = ["#define foreach_api_reply_handler \\\n"]
- for f in func_list:
- name = f['name']
- camelcase_name = util.underscore_to_camelcase(f['name'])
-
- if (not util.is_reply(camelcase_name) and not util.is_notification(name)) or util.is_ignored(name) \
- or util.is_control_ping(camelcase_name):
- continue
-
- handler_registration.append(handler_registration_template.substitute(
- name=name,
- upercase_name=name.upper()))
-
- return "".join(handler_registration)
-
-
-jvpp_c_template = Template("""/**
- * This file contains JNI bindings for jvpp Java API.
- * It was generated by jvpp_c_gen.py based on $inputfile
- * (python representation of api file generated by vppapigen).
- */
-
-// JAVA class reference cache
-$class_cache
-
-// JNI bindings
-$jni_implementations
-
-// Message handlers
-$msg_handlers
-
-// Registration of message handlers in vlib
-$handler_registration
-""")
-
-def generate_jvpp(func_list, plugin_name, inputfile):
- """ Generates jvpp C file """
- print "Generating jvpp C"
-
- class_cache = generate_class_cache(func_list, plugin_name)
- jni_impl = generate_jni_impl(func_list, plugin_name, inputfile)
- msg_handlers = generate_msg_handlers(func_list, plugin_name, inputfile)
- handler_registration = generate_handler_registration(func_list)
-
- jvpp_c_file = open("jvpp_%s_gen.h" % plugin_name, 'w')
- jvpp_c_file.write(jvpp_c_template.substitute(
- inputfile=inputfile,
- class_cache=class_cache,
- jni_implementations=jni_impl,
- msg_handlers=msg_handlers,
- handler_registration=handler_registration))
- jvpp_c_file.flush()
- jvpp_c_file.close()
-