java-native-access/jna · error · IllegalArgumentException
setValue must not be called with type set to NULL
Error message
setValue must not be called with type set to NULL
What it means
EVT_VARIANT.setValue() in JNA's Winevt helper wraps an EVT_VARIANT union for the Windows Event Log API. It throws IllegalArgumentException when the caller passes a null EVT_VARIANT_TYPE, because without a type there is no way to know which union field to populate. The null check runs before any switch on the type, so this always fails fast.
Source
Thrown at contrib/platform/src/com/sun/jna/platform/win32/Winevt.java:274
public boolean isArray() {
return (Type & EVT_VARIANT_TYPE_ARRAY) == EVT_VARIANT_TYPE_ARRAY;
}
public EVT_VARIANT_TYPE getVariantType() {
return EVT_VARIANT_TYPE.values()[getBaseType()];
}
// Helper to store java object for set values
private Object holder;
/**
* @param type
* @param value
*/
public void setValue(EVT_VARIANT_TYPE type, Object value) {
allocateMemory();
if (type == null) {
throw new IllegalArgumentException("setValue must not be called with type set to NULL");
}
holder = null;
if (value == null || type == EVT_VARIANT_TYPE.EvtVarTypeNull) {
Type = EVT_VARIANT_TYPE.EvtVarTypeNull.ordinal();
Count = 0;
field1.writeField("pointerValue", Pointer.NULL);
} else {
switch (type) {
case EvtVarTypeAnsiString:
if (value.getClass().isArray() && value.getClass().getComponentType() == String.class) {
Type = type.ordinal() | EVT_VARIANT_TYPE_ARRAY;
StringArray sa = new StringArray((String[]) value, false);
holder = sa;
Count = ((String[]) value).length;
field1.writeField("pointerValue", sa);
} else if (value.getClass() == String.class) {
Type = type.ordinal();
Memory mem = new Memory(((String) value).length() + 1);View on GitHub (pinned to d036ad9781)
Solutions
- Pass a non-null EVT_VARIANT_TYPE, e.g. EVT_VARIANT_TYPE.EvtVarTypeNull if you intend to clear the variant
- If the type comes from a variable or lookup, check for null before calling setValue and substitute EvtVarTypeNull
- If clearing the value, call setValue(EVT_VARIANT_TYPE.EvtVarTypeNull, null) instead of passing a null type
Example fix
// before variant.setValue(null, myValue); // after variant.setValue(EVT_VARIANT_TYPE.EvtVarTypeString, myValue); // or to clear: variant.setValue(EVT_VARIANT_TYPE.EvtVarTypeNull, null);
Defensive patterns
Strategy: validation
Validate before calling
if (type == null) {
type = EVT_VARIANT_TYPE.EvtVarTypeNull; // or throw a domain-specific error early
}
variant.setValue(type, value); Type guard
boolean isValidType(EVT_VARIANT_TYPE t) { return t != null; } Try / catch
try {
variant.setValue(type, value);
} catch (IllegalArgumentException e) {
log.warn("Bad EVT_VARIANT type/value: " + e.getMessage());
} Prevention
- Never pass a possibly-null enum obtained from a lookup map into setValue
- Default unknown types to EvtVarTypeNull rather than null
- Unit-test channel-config rendering with all EVT_VARIANT_TYPE values
When it happens
Trigger: Calling setValue(null, someValue) — e.g. passing an uninitialized or lookup-failed EVT_VARIANT_TYPE variable, or a method returning null type to renderChannelConfig/event-rendering code like testModifyChannelConfig.
Common situations: Mapping an EvtVariant field whose type was read from a struct and turned out null; passing the result of a map lookup (get(typeKey)) that missed; refactoring where the type variable was accidentally not initialized.
Related errors
- must be set from String/String[]
- must be set from BOOL/BOOL[]
- must be set from byte/byte[]
- must be set from short/short[]
- must be set from int/int[]
AI-assisted analysis of java-native-access/jna@d036ad9781 (2026-09-12).
Data as JSON: /api/errors/6d09fce6b555b7f8.
Report an issue: GitHub.