static void GenerateJniNativeInterface(TextWriter o) { o.WriteLine("#if FEATURE_JNIENVIRONMENT_SAFEHANDLES || FEATURE_JNIENVIRONMENT_JI_INTPTRS || FEATURE_JNIENVIRONMENT_XA_INTPTRS"); o.WriteLine("\t[StructLayout (LayoutKind.Sequential)]"); o.WriteLine("\tpartial struct JniNativeInterfaceStruct {"); o.WriteLine(); int maxName = JNIEnvEntries.Max(e => e.Name.Length); o.WriteLine("#pragma warning disable 0649 // Field is assigned to, and will always have its default value `null`; ignore as it'll be set in native code."); o.WriteLine("#pragma warning disable 0169 // Field never used; ignore since these fields make the structure have the right layout."); for (int i = 0; i < 4; i++) { o.WriteLine("\t\tprivate IntPtr reserved{0}; // void*", i); } foreach (var e in JNIEnvEntries) { o.WriteLine("\t\tpublic IntPtr {0};{1} // {2}", e.Name, new string (' ', maxName - e.Name.Length), e.Prototype); } o.WriteLine("#pragma warning restore 0169"); o.WriteLine("#pragma warning restore 0649"); o.WriteLine("\t}"); o.WriteLine("#endif // FEATURE_JNIENVIRONMENT_SAFEHANDLES || FEATURE_JNIENVIRONMENT_JI_INTPTRS || FEATURE_JNIENVIRONMENT_XA_INTPTRS"); }
static void GenerateTypes(TextWriter o, HandleStyle style) { if (style == HandleStyle.JIIntPtrPinvokeWithErrors) { GenerateNativeMethods(o, style); } var visibilities = new Dictionary <string, string> { { ArrayOperationsCategory, "public" }, { ClassesCategory, "public" }, { ExceptionsCategory, "public" }, { InstanceFieldsCategory, "public" }, { InstanceMethodsCategory, "public" }, { MonitorOperationsCategory, "public" }, { NIOSupportCategory, "public" }, { ObjectOperationsCategory, "public" }, { ReferencesCatgeory, "public" }, { StaticFieldsCategory, "public" }, { StaticMethodsCategory, "public" }, { StringOperationsCategory, "public" }, }; o.WriteLine("\tpartial class JniEnvironment {"); foreach (var t in JNIEnvEntries .Select(e => e.DeclaringType ?? "JniEnvironment") .Distinct() .OrderBy(t => t)) { string visibility; if (!visibilities.TryGetValue(t, out visibility)) { visibility = "internal"; } GenerateJniEnv(o, t, visibility, style); } o.WriteLine("\t}"); }
static void GenerateJniEnv(TextWriter o) { o.WriteLine("\tpublic static partial class JNIEnv {"); foreach (JniFunction entry in JNIEnvEntries) { if (entry.Parameters == null) { continue; } o.WriteLine(); if (!useJavaInterop) { CreateDelegate(o, entry); } if (entry.IsPrivate || entry.CustomWrapper) { continue; } switch (entry.ApiName) { case "NewArray": var copyArray = JNIEnvEntries.Single(e => e.Name.StartsWith("Get") && e.Name.EndsWith("ArrayRegion") && e.Parameters [0].Type.Type == entry.ReturnType.Type); o.Write("\t\t{2} static {0} {1} (", entry.ReturnType.ManagedType, entry.ApiName, entry.Visibility); o.WriteLine("{0} array)", copyArray.Parameters [3].Type.ManagedType); o.WriteLine("\t\t{"); o.WriteLine("\t\t\tif (array == null)"); o.WriteLine("\t\t\t\treturn IntPtr.Zero;"); if (useJavaInterop) { o.WriteLine("\t\t\tJniObjectReference result;"); o.WriteLine("\t\t\tresult = JniEnvironment.{0}.{1} (array.Length);", entry.DeclaringType, entry.Name); o.WriteLine("\t\t\tCopyArray (array, result.Handle);"); o.WriteLine("\t\t\treturn result.Handle;"); o.WriteLine("\t\t}"); break; } o.WriteLine("\t\t\tIntPtr result;"); o.WriteLine("\t\t\tresult = Env.{0} (Handle, array.Length);", entry.Name); RaiseException(o, entry); o.WriteLine("\t\t\tCopyArray (array, result);"); o.WriteLine("\t\t\treturn result;"); o.WriteLine("\t\t}"); break; case "CopyArray": o.Write("\t\t{2} static unsafe {0} {1} (", entry.ReturnType.ManagedType, entry.ApiName, entry.Visibility); if (entry.Name.StartsWith("G")) { o.WriteLine("IntPtr src, {0} dest)", entry.Parameters [3].Type.ManagedType); o.WriteLine("\t\t{"); o.WriteLine("\t\t\tif (src == IntPtr.Zero)"); o.WriteLine("\t\t\t\treturn;"); if (useJavaInterop) { var t = entry.Parameters [3].Type.ManagedType.Replace("[]", "*"); o.WriteLine("\t\t\tfixed ({0} __p = dest)", t); o.WriteLine("\t\t\t\tJniEnvironment.{0}.{1} (new JniObjectReference (src), 0, dest.Length, {2}__p);", entry.DeclaringType, entry.Name, t == "byte*" ? "(sbyte*) " : ""); o.WriteLine("\t\t}"); break; } o.WriteLine("\t\t\tEnv.{0} (Handle, src, 0, dest.Length, dest);", entry.Name); } else { o.WriteLine("{0} src, IntPtr dest)", entry.Parameters [3].Type.ManagedType); o.WriteLine("\t\t{"); o.WriteLine("\t\t\tif (src == null)"); o.WriteLine("\t\t\t\tthrow new ArgumentNullException (\"src\");"); if (useJavaInterop) { var t = entry.Parameters [3].Type.ManagedType.Replace("[]", "*"); o.WriteLine("\t\t\tfixed ({0} __p = src)", t); o.WriteLine("\t\t\t\tJniEnvironment.{0}.{1} (new JniObjectReference (dest), 0, src.Length, {2}__p);", entry.DeclaringType, entry.Name, t == "byte*" ? "(sbyte*) " : ""); o.WriteLine("\t\t}"); break; } o.WriteLine("\t\t\tEnv.{0} (Handle, dest, 0, src.Length, src);", entry.Name); } RaiseException(o, entry); o.WriteLine("\t\t}"); break; default: GenerateDefaultJniFunction(o, entry); break; } } o.WriteLine("\t}"); }