NationalSecurityAgency/ghidra · error · SQLException

Optional table: column type mismatch

Error message

Optional table: column type mismatch

What it means

BSim supports optional metadata tables (extra key/value tables). `getOptionalTable` searches existing optional tables by name; if one is found whose key or value column types differ from the requested `keyType`/`valueType`, it throws SQLException. This refuses to silently read data under a mismatched schema.

Source

Thrown at Ghidra/Features/BSim/src/main/java/ghidra/features/bsim/query/client/AbstractSQLFunctionDatabase.java:772

	 * Establish an optional key/value table with this connection.
	 * The OptionalTable object is created and added to the list for this connection.
	 * If the caller desires, the table is tested for existence. If it doesn't
	 * exist, the object is not added to the list and null is returned.
	 * @param tableName is the name of the SQL table
	 * @param keyType is the type-code of the key column
	 * @param valueType is the type-code of the value column
	 * @param testExistence if true, we test the existence of the table
	 * @return the OptionalTable or null
	 * @throws SQLException for problems with the connection, or if
	 *     the table exists with different column types
	 */
	private OptionalTable getOptionalTable(String tableName, int keyType, int valueType,
			boolean testExistence) throws SQLException {
		if (optionaltables != null) {		// Search for existing table
			for (OptionalTable table : optionaltables) {
				if (table.getName().equals(tableName)) {
					if (keyType != table.getKeyType() || valueType != table.getValueType()) {
						throw new SQLException("Optional table: column type mismatch");
					}
					return table;
				}
			}
		}
		// If we reach here, table object doesn't exist, so we create it
		OptionalTable table = new OptionalTable(tableName, keyType, valueType, db);
		if (testExistence) {			// If the user requested
			if (!table.exists()) {		//    test for the existence of the table
				table.close();
				return null;			// If it doesn't exist, don't save new table object, return null
			}
		}
		// Insert the new table object at the end of the list
		OptionalTable[] newArray;
		if (optionaltables != null) {
			newArray = Arrays.copyOf(optionaltables, optionaltables.length + 1);
			newArray[optionaltables.length] = table;

View on GitHub (pinned to d5f144c24d)

Solutions

  1. Drop the offending optional table and let BSim recreate it with the correct types.
  2. Align client and server BSim versions so both expect the same schema.
  3. Re-run the official BSim migration tooling to normalize the schema.
  4. If data must be preserved, export, drop, recreate, and re-import.
Defensive patterns

Strategy: validation

Validate before calling

// Before requesting an optional table, verify its column types match expectations.
String sql = "SELECT column_name, data_type FROM information_schema.columns " +
    "WHERE table_name = ? ORDER BY ordinal_position";
try (Connection c = ds.getConnection();
     PreparedStatement ps = c.prepareStatement(sql)) {
    ps.setString(1, tableName);
    ResultSet rs = ps.executeQuery();
    // compare returned types against the keyType/valueType you intend to request
}

Try / catch

try {
    OptionalTable t = db.getOptionalTable(name, keyType, valueType, true);
} catch (SQLException e) {
    if (e.getMessage().equals("Optional table: column type mismatch")) {
        // schema incompatibility -- align versions or recreate the table
        throw new SchemaIncompatibleException(name, e);
    }
    throw e;
}

Prevention

When it happens

Trigger: A database created under one BSim version defined an optional table with certain column types; a later access requests the same table name with different types -- e.g. after an incomplete schema migration or with mixed client/server versions.

Common situations: Version skew between BSim client and server; a manual ALTER TABLE on an optional table; partial/aborted migration; two deployments sharing one DB with divergent schemas.

Related errors


AI-assisted analysis of NationalSecurityAgency/ghidra@d5f144c24d (2026-08-14). Data as JSON: /api/errors/16ac94a0e9c6c7fa. Report an issue: GitHub.