Can someone explain to me why the following structure size is 16 ?
public class StringStruct extends Structure {
public char[] data = new char[4];
public StringStruct() {}
@Override
protected List<String> getFieldOrder() {
return Collections.singletonList("data");
}
}
public class Main {
public static void main(String[] args) {
StringStruct ss = new StringStruct();
// Prints StringStruct: 16
// I was expecting 4...
System.out.println("StringStruct: " + ss.size());
}
}
I want to model structures which own their data
typedef struct {
char data[4];
} StringStruct_s
If I use a byte array instead, it returns the expected value. Still, the char array size is really surprising to me. Is the field interpreted as owning an encoded String ?
So, I launched this executable with various explicit encodings (-Djna.encoding="..."
) to see if it had an effect. No change...
In JNA
, Java char can be mapped to either 16-bit
or 32-bit
character.
It means that you have: 32/8 * 4 = 16
https://github.com/java-native-access/jna/blob/master/www/Mappings.md
Try something like this on your machine
int main() {
printf("%ld\n",sizeof(wchar_t));
}
Update
As mentioned by @Daniel, it's worth noting that mapping C
based char
should be done via byte
.
For this class
interface CLibrary extends Library {
public CLibrary.Data.ByVal GetDataValue();
public CLibrary.Data.ByRef GetDataAllocated();
public class Data extends Structure {
public static final List<String> FIELDS = List.of("array");
public static class ByVal extends Data implements Structure.ByValue {}
public static class ByRef extends Data implements Structure.ByReference {}
public byte[] array = new byte[4];
@Override
protected List<String> getFieldOrder() {
return FIELDS;
}
}
}
you will get size as expected: 4