Invocar llamadas de sistema desde Java

12

¿Hay alguna manera de invocar syscalls directamente desde Java, o es necesario llamar primero a un método nativo?

santiago.basulto
fuente

Respuestas:

11

Necesita usar un método nativo, pero no necesita implementarlo usted mismo. Java tiene una variación en JNI llamada JNA (Java Native Access) , que le permite acceder a bibliotecas compartidas directamente sin necesidad de una interfaz JNI envuelta alrededor de ellas, por lo que puede usar eso para interactuar directamente con glibc:

import com.sun.jna.Library;
import com.sun.jna.Native;

public class Test {
    public interface CStdLib extends Library {
        int syscall(int number, Object... args);
    }

    public static void main(String[] args) {
        CStdLib c = (CStdLib)Native.loadLibrary("c", CStdLib.class);

        // WARNING: These syscall numbers are for x86 only
        System.out.println("PID: " + c.syscall(20));
        System.out.println("UID: " + c.syscall(24));
        System.out.println("GID: " + c.syscall(47));
        c.syscall(39, "/tmp/create-new-directory-here");
    }
}
Michael Mrozek
fuente
interesante, ¿es posible usar nombres de funciones en lugar de números?
maxschlepzig
1
@max en la syscallinterfaz? No, syscalltoma un número entero para representar la llamada apropiada a realizar, al igual que en el lado C. Hay un montón de correos #defineelectrónicos /usr/include/asm/unistd.h, como #define __NR_mkdir 39para que sea más fácil para las personas que llaman a la función C, pero no creo que haya ninguna forma de importarlos automáticamente en Java, tendrías que definirlos todos tú mismo
Michael Mrozek
2
Tenga cuidado: los números en x86 y x86-64 son diferentes en Linux.
Maciej Piechotka
@Maciej Buen punto, agregó una advertencia en la respuesta
Michael Mrozek
Gran respuesta hermano! Gracias por tu ayuda. Desde aquí tengo otra pregunta. Lo preguntaré en un minuto.
santiago.basulto
2

Es necesario utilizar un método nativo o una biblioteca que lo haga por usted.

bmargulies
fuente