带有JNA的函数scanf
我正在尝试使用JNA的scanf
函数:
package importDLLs; import com.sun.jna.Library; import com.sun.jna.Native; public class JNATest { public interface CLibrary extends Library { CLibrary clib = (CLibrary) Native.loadLibrary("msvcrt", CLibrary.class); void printf(String format, Object... args); int sprintf(byte[] speicher, String format, Object...args); int scanf (String format, Object... args1); } public static void main(String[] args) { CLibrary.clib.printf("Hello World"); String test= null; args = new String[2]; args[0]="This is a test"; args[1]="and another one"; for ( int i = 0; i < args.length; i++ ){ CLibrary.clib.printf( "\nArgument %d : %s",i, args[ i ] ); } CLibrary.clib.printf("\nBitte Namen eingeben"); CLibrary.clib.scanf("%s", test); CLibrary.clib.printf("\nyour name is %s",test); } }
我是新手,我也读了很多关于JNA的内容。 但我无法弄清楚如何使用它。 printf
函数没有问题。
这是我得到的错误,当我启动它并在我向控制台写入内容之后。
Java运行时环境检测到致命错误:
pc = 0x000007fefe531435,pid = 10168,tid = 2964,EXCEPTION_ACCESS_VIOLATION(0xc0000005)
JRE版本:7.0_03-b05 Java VM:Java HotSpot(TM)64位服务器VM(22.1-b02混合模式windows-amd64压缩oops)有问题的框架:C [msvcrt.dll + 0x61435]
无法编写核心转储。 默认情况下,在客户端版本的Windows上未启用小型转储
包含更多信息的错误报告文件保存为:***** \ URC Lab \ hs_err_pid10168.log
如果您想提交错误报告,请访问:
http://bugreport.sun.com/bugreport/crash.jsp
:http://bugreport.sun.com/bugreport/crash.jsp
崩溃发生在Java虚拟机之外的本机代码中。 查看有问题的框架,了解在哪里报告错误。
节目输出:
Hello World Argument 0 : This is a test Argument 1 : and another one your name is
为什么我会收到错误,我该如何解决?
仔细阅读scanf
的手册页。 每个varargs参数必须是可以写入扫描项目的内存的地址(即指针)。
Java String
是一个不可变对象。 这意味着你不能写信给它。
可写缓冲区包括原始数组(例如byte[]
),JNA Memory
或NIO缓冲区。 在这种情况下,我建议使用足够大小的Memory
,然后使用其getString()
方法将本机NUL终止的C字符串作为Java String
提取。
对于扫描其他类型,JNA提供了ByReference
及其子类,它提供了常见的native &var
表示法的function。
一个例子,正如@Gary建议的那样:
import com.sun.jna.Library; import com.sun.jna.Native; import com.sun.jna.Platform; import com.sun.jna.Pointer; public interface JNAApiInterface extends Library { JNAApiInterface INSTANCE = (JNAApiInterface) Native.loadLibrary((Platform.isWindows() ? "msvcrt" : "c"), JNAApiInterface.class); Pointer __iob_func(); int sizeOfFileStructure = Platform.is64Bit() ? 48 : 32; Pointer stdout = JNAApiInterface.INSTANCE.__iob_func().share(sizeOfFileStructure); void printf(String format, Object... args); int sprintf(byte[] buffer, String format, Object... args); int scanf(String format, Object... args); int fflush (Pointer stream); int puts(String format) ; int fprintf(Pointer stream, String format, Object...args) ; void setbuf(Pointer stream, String buffer) ; } import com.sun.jna.Memory; import com.sun.jna.platform.win32.Kernel32; public class JNABucket { public static void main(String args[]) { JNAApiInterface jnaLib = JNAApiInterface.INSTANCE; Kernel32 klib = Kernel32.INSTANCE; Memory userName = new Memory(256); jnaLib.setbuf(jnaLib.stdout, null); jnaLib.printf("Hello World"); for (int i = 0; i < args.length; i++) { jnaLib.printf("\nArgument %d : %s", i, args[i]); } jnaLib.puts("\nPlease Enter Your Name:\n"); jnaLib.scanf("%s", userName); jnaLib.printf("\nYour name is: %s", userName); jnaLib.fprintf(jnaLib.stdout, "\nThis is a Test"); } }
import com.sun.jna.Library; import com.sun.jna.Native; import com.sun.jna.Platform; import com.sun.jna.Pointer; public interface JNAApiInterface extends Library { JNAApiInterface INSTANCE = (JNAApiInterface) Native.loadLibrary((Platform.isWindows() ? "msvcrt" : "c"), JNAApiInterface.class); Pointer __iob_func(); int sizeOfFileStructure = Platform.is64Bit() ? 48 : 32; Pointer stdout = JNAApiInterface.INSTANCE.__iob_func().share(sizeOfFileStructure); void printf(String format, Object... args); int sprintf(byte[] buffer, String format, Object... args); int scanf(String format, Object... args); int fflush (Pointer stream); int puts(String format) ; int fprintf(Pointer stream, String format, Object...args) ; void setbuf(Pointer stream, String buffer) ; } import com.sun.jna.Memory; import com.sun.jna.platform.win32.Kernel32; public class JNABucket { public static void main(String args[]) { JNAApiInterface jnaLib = JNAApiInterface.INSTANCE; Kernel32 klib = Kernel32.INSTANCE; Memory testName = new Memory(256); jnaLib.setbuf(jnaLib.stdout, null); jnaLib.printf("Hello World"); for (int i = 0; i < args.length; i++) { jnaLib.printf("\nArgument %d : %s", i, args[i]); } jnaLib.puts("\nPlease Enter Your Name:\n"); jnaLib.scanf("%s", testName); jnaLib.printf("\nYour name is: %s", testName); jnaLib.fprintf(jnaLib.stdout, "\nthis is a Test"); } }
我发现这个解决方案来修复“scanf”无效的内存访问问题,并立即使用printf和puts函数将文本打印到控制台。
- 当项目转换为可执行jar时,序列化文件不起作用?
- 将自然语言描述解析为结构化数据的策略
- 使用JSON的Jersey RESTfull服务
- 如何使用Java配置在Tomcat 8中配置JNDI DataSource:
- 使用hibernate Criteria更新多行
- 执行中出现Hadoop错误:键入map中的键不匹配:期望org.apache.hadoop.io.Text,收到org.apache.hadoop.io.LongWritable
- 无法获得在Spring Security中使用的@Secured Method Security注释
- java支持if-then-else regexp构造(Perl构造)吗?
- 您建议使用哪种压缩(GZIP最受欢迎)servletfilter?