java-native-access/jna · error · ClassCastException

Unable to cast to CFBoolean. Type ID

Error message

Unable to cast to CFBoolean. Type ID: {getTypeID()}

What it means

CFBooleanRef's Pointer constructor verifies via CFGetTypeID that the wrapped native object is a CFBoolean. When the type id differs (including id 0 for a NULL pointer), it throws ClassCastException to prevent an invalid CFBoolean downcast.

Solutions

  1. Test the type first: new CFTypeRef(p).isTypeID(CoreFoundation.BOOLEAN_TYPE_ID) before constructing CFBooleanRef.
  2. Handle CFNumber 0/1 as a boolean fallback when dictionaries encode flags as numbers.
  3. Null-check the pointer; a missing key yields NULL with type id 0.
  4. Coerce common alternatives (CFNumber 0/1, CFString "true"/"YES") if the source data is heterogeneous.

Example fix

// before
CFBooleanRef b = new CFBooleanRef(value); // throws ClassCastException
// after
CFTypeRef ref = new CFTypeRef(value);
CFBooleanRef b = ref.isTypeID(CoreFoundation.BOOLEAN_TYPE_ID)
    ? new CFBooleanRef(value)
    : null; // handle non-boolean case
Defensive patterns

Strategy: type-guard

Validate before calling

if (value != null && new CFTypeRef(value).isTypeID(CoreFoundation.BOOLEAN_TYPE_ID)) {
    CFBooleanRef b = new CFBooleanRef(value);
}

Type guard

boolean isCFBoolean(Pointer p) {
    return p != null && new CFTypeRef(p).isTypeID(CoreFoundation.BOOLEAN_TYPE_ID);
}

Try / catch

try {
    boolean flag = new CFBooleanRef(value).booleanValue();
} catch (ClassCastException e) {
    // fall back: treat CFNumber 0/1 as boolean or default false
}

Prevention

When it happens

Trigger: Constructing new CFBooleanRef(pointer) from a value fetched via CFDictionaryGetValue, CFArrayGetValueAtIndex, or notification/user-default lookups where the value is a CFString, CFNumber, CFArray, or NULL.

Common situations: Assuming a boolean flag in a CFDictionary is stored as CFBoolean when the producer stored 0/1 as CFNumber; reading nil dictionary entries; mismatched expectations after an API/OS version changed the stored representation.

Understand the failure class

Background: Type mismatch errors: IllegalArgumentException, TypeError and type guards across 150 open-source libraries — this error's family across 150 libraries.

Related errors


AI-assisted analysis of java-native-access/jna@d036ad9781 (2026-09-12). Data as JSON: /api/errors/f1b0626ab77120bd. Report an issue: GitHub.

Appendix: source

Thrown at contrib/platform/src/com/sun/jna/platform/mac/CoreFoundation.java:287

         * @return a {@link CFIndex} representing the enum ordinal.
         */
        public CFIndex typeIndex() {
            return new CFIndex(this.ordinal());
        }
    }

    /**
     * A reference to a {@code CFBoolean} object.
     */
    class CFBooleanRef extends CFTypeRef {
        public CFBooleanRef() {
            super();
        }

        public CFBooleanRef(Pointer p) {
            super(p);
            if (!isTypeID(BOOLEAN_TYPE_ID)) {
                throw new ClassCastException("Unable to cast to CFBoolean. Type ID: " + getTypeID());
            }
        }

        /**
         * Convert a reference to a Core Foundations Boolean into its {@code boolean}
         *
         * @return The corresponding {@code boolean}
         */
        public boolean booleanValue() {
            return 0 != INSTANCE.CFBooleanGetValue(this);
        }
    }

    /**
     * A reference to an immutable {@code CFArray} object.
     * <p>
     * CFArray is “toll-free bridged” with its Cocoa Foundation counterpart,
     * {@code NSArray}. Therefore, in a method where you see an {@code NSArray *}

View on GitHub (pinned to d036ad9781)