{"record":{"id":"484de67e6d844457","repo":"NationalSecurityAgency/ghidra","slug":"property-has-type-not","errorCode":null,"errorMessage":"Property {} has type {}, not {}","messagePattern":"Property (.+?) has type (.+?), not (.+?)","errorType":"validation","errorClass":"TypeMismatchException","httpStatus":null,"severity":"error","filePath":"Ghidra/Debug/Framework-TraceModeling/src/main/java/ghidra/trace/database/property/DBTraceAddressPropertyManager.java","lineNumber":195,"sourceCode":"\t\t\tDBTraceAddressPropertyEntry ent = propertyStore.create();\n\t\t\tent.set(name, valueClass);\n\t\t\tAbstractDBTracePropertyMap<T, ?> map = doCreateMap(name, OpenMode.CREATE, valueClass);\n\t\t\tent.map = map;\n\t\t\tpropertyMapsByName.put(name, map);\n\t\t\treturn map;\n\t\t}\n\t}\n\n\t@Override\n\t@SuppressWarnings(\"unchecked\")\n\tpublic <T> AbstractDBTracePropertyMap<T, ?> getPropertyMap(String name, Class<T> valueClass) {\n\t\ttry (LockHold hold = LockHold.lock(lock.readLock())) {\n\t\t\tAbstractDBTracePropertyMap<?, ?> map = propertyMapsByName.get(name);\n\t\t\tif (map == null) {\n\t\t\t\treturn null;\n\t\t\t}\n\t\t\tif (valueClass != map.getValueClass()) {\n\t\t\t\tthrow new TypeMismatchException(\"Property \" + name + \" has type \" +\n\t\t\t\t\tmap.getValueClass() + \", not \" + valueClass);\n\t\t\t}\n\t\t\treturn (AbstractDBTracePropertyMap<T, ?>) map;\n\t\t}\n\t}\n\n\t@Override\n\t@SuppressWarnings(\"unchecked\")\n\tpublic <T> TracePropertyMap<? extends T> getPropertyMapExtends(String name,\n\t\t\tClass<T> valueClass) {\n\t\ttry (LockHold hold = LockHold.lock(lock.readLock())) {\n\t\t\tAbstractDBTracePropertyMap<?, ?> map = propertyMapsByName.get(name);\n\t\t\tif (map == null) {\n\t\t\t\treturn null;\n\t\t\t}\n\t\t\tif (!valueClass.isAssignableFrom(map.getValueClass())) {\n\t\t\t\tthrow new TypeMismatchException(\"Property \" + name + \" has type \" +\n\t\t\t\t\tmap.getValueClass() + \", which does not extend \" + valueClass);","sourceCodeStart":177,"sourceCodeEnd":213,"githubUrl":"https://github.com/NationalSecurityAgency/ghidra/blob/d5f144c24d6bc53c9cbf4448c6d11143e7696206/Ghidra/Debug/Framework-TraceModeling/src/main/java/ghidra/trace/database/property/DBTraceAddressPropertyManager.java#L177-L213","documentation":"Thrown as TypeMismatchException by getPropertyMap(name, valueClass) when a map exists under name but its stored value class is not exactly equal to the requested valueClass. Equality is by reference identity (==) on the Class objects, so even a compatible subtype will fail this strict variant. Use getPropertyMapExtends for subtype-tolerant lookup.","triggerScenarios":"A map was created as String.class but queried with getPropertyMap(\"note\", Object.class), or created as a Saveable subclass and queried with the parent Saveable class.","commonSituations":"Two modules share a property name but disagree on the declared value type; refactoring changed a value class while a persisted trace stores the old class.","solutions":["Query with the exact class the map was created with (check via getPropertyMap(name).getValueClass()).","If you only need a supertype view, call getPropertyMapExtends(name, supertype.class).","If you only need a subtype view, call getPropertyMapSuper (the inverse-tolerant getter)."],"exampleFix":"// before\nTracePropertyMap<String> m = mgr.getPropertyMap(\"note\", Object.class);\n// after\nTracePropertyMap<? extends Object> m =\n    mgr.getPropertyMapExtends(\"note\", Object.class);","handlingStrategy":"validation","validationCode":"AbstractDBTracePropertyMap<?,?> existing = mgr.getPropertyMap(name);\nif (existing == null) return null;\nif (existing.getValueClass() != valueClass) {\n    // decide: use extends/super getter or fail\n}\nreturn mgr.getPropertyMap(name, valueClass);","typeGuard":"static boolean sameValueClass(AbstractDBTracePropertyMap<?,?> m, Class<?> c) {\n    return m.getValueClass() == c;\n}","tryCatchPattern":"try { return mgr.getPropertyMap(name, cls); }\ncatch (TypeMismatchException e) { /* inspect getValueClass */ }","preventionTips":["Query with the exact stored class; inspect getValueClass() first.","Use the extends/super getters when you need variance."],"tags":["property-map","type-mismatch","generics"],"backgroundTag":null,"analyzedSha":"d5f144c24d6bc53c9cbf4448c6d11143e7696206","analyzedAt":"2026-08-14T01:00:57.564Z","schemaVersion":2},"datasetVersion":"2026-08-14T05:17:29.042Z"}