117c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpepackage SQLite.JDBC2z;
2417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
3417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughesimport java.sql.*;
4417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughesimport java.util.*;
5417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
6417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughespublic class JDBCConnection
7417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    implements java.sql.Connection, SQLite.BusyHandler {
8417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
9417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    /**
10417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes     * Open database.
11417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes     */
12417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    protected DatabaseX db;
13417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
14417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    /**
15417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes     * Database URL.
16417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes     */
17417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    protected String url;
18417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
19417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    /**
20417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes     * Character encoding.
21417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes     */
22417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    protected String enc;
23417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
24417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    /**
257a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes     * SQLite 3 VFS to use.
267a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes     */
277a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes    protected String vfs;
287a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes
297a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes    /**
30417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes     * Autocommit flag, true means autocommit.
31417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes     */
32417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    protected boolean autocommit = true;
33417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
34417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    /**
35417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes     * In-transaction flag.
36417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes     * Can be true only when autocommit false.
37417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes     */
38417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    protected boolean intrans = false;
39417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
40417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    /**
41417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes     * Timeout for Database.exec()
42417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes     */
43417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    protected int timeout = 1000000;
44417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
45417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    /**
467a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes     * Use double/julian date representation.
477a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes     */
487a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes    protected boolean useJulian = false;
497a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes
507a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes    /**
51417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes     * File name of database.
52417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes     */
53417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    private String dbfile = null;
54417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
55417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    /**
56417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes     * Reference to meta data or null.
57417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes     */
58417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    private JDBCDatabaseMetaData meta = null;
59417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
60417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    /**
61417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes     * Base time value for timeout handling.
62417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes     */
63417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    private long t0;
64417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
65417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    /**
66417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes     * Database in readonly mode.
67417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes     */
68417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    private boolean readonly = false;
69417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
707a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes    /**
717a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes     * Transaction isolation mode.
727a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes     */
737a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes    private int trmode = TRANSACTION_SERIALIZABLE;
74417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
75417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    private boolean busy0(DatabaseX db, int count) {
767a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	if (count <= 1) {
777a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    t0 = System.currentTimeMillis();
787a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
797a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	if (db != null) {
807a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    long t1 = System.currentTimeMillis();
817a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    if (t1 - t0 > timeout) {
827a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		return false;
837a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    }
847a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    db.wait(100);
857a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    return true;
867a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
877a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	return false;
88417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
89417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
90417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public boolean busy(String table, int count) {
917a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	return busy0(db, count);
92417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
93417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
94417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    protected boolean busy3(DatabaseX db, int count) {
957a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	if (count <= 1) {
967a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    t0 = System.currentTimeMillis();
977a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
987a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	if (db != null) {
997a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    long t1 = System.currentTimeMillis();
1007a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    if (t1 - t0 > timeout) {
1017a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		return false;
1027a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    }
1037a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    return true;
1047a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
1057a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	return false;
106417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
107417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
108417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    private DatabaseX open(boolean readonly) throws SQLException {
1097a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	DatabaseX dbx = null;
1107a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	try {
1117a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    dbx = new DatabaseX();
1127a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    dbx.open(dbfile, readonly ? SQLite.Constants.SQLITE_OPEN_READONLY :
1137a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		     (SQLite.Constants.SQLITE_OPEN_READWRITE |
1147a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		      SQLite.Constants.SQLITE_OPEN_CREATE), vfs);
1157a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    dbx.set_encoding(enc);
1167a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	} catch (SQLite.Exception e) {
1177a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    throw new SQLException(e.toString());
1187a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
1197a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	int loop = 0;
1207a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	while (true) {
1217a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    try {
1227a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		dbx.exec("PRAGMA short_column_names = off;", null);
1237a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		dbx.exec("PRAGMA full_column_names = on;", null);
1247a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		dbx.exec("PRAGMA empty_result_callbacks = on;", null);
1257a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		if (SQLite.Database.version().compareTo("2.6.0") >= 0) {
1267a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		    dbx.exec("PRAGMA show_datatypes = on;", null);
1277a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		}
1287a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    } catch (SQLite.Exception e) {
1297a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		if (dbx.last_error() != SQLite.Constants.SQLITE_BUSY ||
1307a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		    !busy0(dbx, ++loop)) {
1317a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		    try {
1327a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes			dbx.close();
1337a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		    } catch (SQLite.Exception ee) {
1347a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		    }
1357a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		    throw new SQLException(e.toString());
1367a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		}
1377a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		continue;
1387a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    }
1397a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    break;
1407a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
1417a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	return dbx;
1427a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes    }
1437a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes
1447a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes    public JDBCConnection(String url, String enc, String pwd, String drep,
1457a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes			  String vfs)
1467a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	throws SQLException {
1477a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	if (url.startsWith("sqlite:/")) {
1487a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    dbfile = url.substring(8);
1497a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	} else if (url.startsWith("jdbc:sqlite:/")) {
1507a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    dbfile = url.substring(13);
1517a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	} else {
1527a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    throw new SQLException("unsupported url");
1537a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
1547a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	this.url = url;
1557a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	this.enc = enc;
1567a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	this.vfs = vfs;
1577a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	try {
1587a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    db = open(readonly);
1597a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    try {
1607a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		if (pwd != null && pwd.length() > 0) {
1617a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		    db.key(pwd);
1627a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		}
1637a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    } catch (SQLite.Exception se) {
1647a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		throw new SQLException("error while setting key");
1657a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    }
1667a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    db.busy_handler(this);
1677a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	} catch (SQLException e) {
1687a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    if (db != null) {
1697a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		try {
1707a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		    db.close();
1717a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		} catch (SQLite.Exception ee) {
1727a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		}
1737a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    }
1747a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    throw e;
1757a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
1767a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	useJulian = drep != null &&
1777a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    (drep.startsWith("j") || drep.startsWith("J"));
178417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
179417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
180417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    /* non-standard */
181417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public SQLite.Database getSQLiteDatabase() {
1827a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	return (SQLite.Database) db;
183417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
184417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
185417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public Statement createStatement() {
1867a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	JDBCStatement s = new JDBCStatement(this);
1877a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	return s;
188417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
1897a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes
190417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public Statement createStatement(int resultSetType,
1917a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes				     int resultSetConcurrency)
1927a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	throws SQLException {
1937a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	if (resultSetType != ResultSet.TYPE_FORWARD_ONLY &&
1947a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    resultSetType != ResultSet.TYPE_SCROLL_INSENSITIVE &&
1957a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    resultSetType != ResultSet.TYPE_SCROLL_SENSITIVE) {
19617c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	    throw new SQLFeatureNotSupportedException("unsupported result set type");
1977a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
1987a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	if (resultSetConcurrency != ResultSet.CONCUR_READ_ONLY &&
1997a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    resultSetConcurrency != ResultSet.CONCUR_UPDATABLE) {
20017c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	    throw new SQLFeatureNotSupportedException("unsupported result set concurrency");
2017a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
2027a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	JDBCStatement s = new JDBCStatement(this);
2037a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	return s;
2047a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes    }
2057a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes
206417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public DatabaseMetaData getMetaData() throws SQLException {
2077a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	if (meta == null) {
2087a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    meta = new JDBCDatabaseMetaData(this);
2097a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
2107a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	return meta;
211417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
212417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
213417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public void close() throws SQLException {
2147a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	try {
2157a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    rollback();
2167a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	} catch (SQLException e) {
2177a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    /* ignored */
2187a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
2197a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	intrans = false;
2207a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	if (db != null) {
2217a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    try {
2227a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		db.close();
2237a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		db = null;
2247a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    } catch (SQLite.Exception e) {
2257a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		throw new SQLException(e.toString());
2267a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    }
2277a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
228417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
229417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
230417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public boolean isClosed() throws SQLException {
2317a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	return db == null;
232417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
233417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
234417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public boolean isReadOnly() throws SQLException {
2357a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	return readonly;
236417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
237417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
238417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public void clearWarnings() throws SQLException {
239417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
240417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
241417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public void commit() throws SQLException {
2427a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	if (db == null) {
2437a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    throw new SQLException("stale connection");
2447a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
2457a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	if (!intrans) {
2467a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    return;
2477a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
2487a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	try {
2497a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    db.exec("COMMIT", null);
2507a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    intrans = false;
2517a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	} catch (SQLite.Exception e) {
2527a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    throw new SQLException(e.toString());
2537a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
254417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
255417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
256417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public boolean getAutoCommit() throws SQLException {
2577a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	return autocommit;
258417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
259417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
260417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public String getCatalog() throws SQLException {
2617a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	return null;
262417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
263417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
264417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public int getTransactionIsolation() throws SQLException {
2657a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	return trmode;
266417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
267417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
268417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public SQLWarning getWarnings() throws SQLException {
2697a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	return null;
270417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
271417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
272417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public String nativeSQL(String sql) throws SQLException {
2737a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	throw new SQLException("not supported");
274417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
275417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
276417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public CallableStatement prepareCall(String sql) throws SQLException {
2777a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	throw new SQLException("not supported");
278417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
279417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
280417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public CallableStatement prepareCall(String sql, int x, int y)
2817a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	throws SQLException {
28217c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	throw new SQLFeatureNotSupportedException();
283417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
284417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
285417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public PreparedStatement prepareStatement(String sql) throws SQLException {
2867a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	JDBCPreparedStatement s = new JDBCPreparedStatement(this, sql);
2877a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	return s;
288417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
289417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
290417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public PreparedStatement prepareStatement(String sql, int resultSetType,
2917a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes					      int resultSetConcurrency)
2927a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	throws SQLException {
2937a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	if (resultSetType != ResultSet.TYPE_FORWARD_ONLY &&
2947a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    resultSetType != ResultSet.TYPE_SCROLL_INSENSITIVE &&
2957a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    resultSetType != ResultSet.TYPE_SCROLL_SENSITIVE) {
29617c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	    throw new SQLFeatureNotSupportedException("unsupported result set type");
2977a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
2987a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	if (resultSetConcurrency != ResultSet.CONCUR_READ_ONLY &&
2997a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    resultSetConcurrency != ResultSet.CONCUR_UPDATABLE) {
30017c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	    throw new SQLFeatureNotSupportedException("unsupported result set concurrency");
3017a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
3027a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	JDBCPreparedStatement s = new JDBCPreparedStatement(this, sql);
3037a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	return s;
304417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
305417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
306417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public void rollback() throws SQLException {
3077a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	if (db == null) {
3087a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    throw new SQLException("stale connection");
3097a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
3107a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	if (!intrans) {
3117a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    return;
3127a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
3137a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	try {
3147a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    db.exec("ROLLBACK", null);
3157a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    intrans = false;
3167a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	} catch (SQLite.Exception e) {
3177a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    throw new SQLException(e.toString());
3187a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
319417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
320417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
321417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public void setAutoCommit(boolean ac) throws SQLException {
3227a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	if (ac && intrans && db != null) {
3237a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    try {
3247a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		db.exec("ROLLBACK", null);
3257a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    } catch (SQLite.Exception e) {
3267a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		throw new SQLException(e.toString());
3277a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    } finally {
3287a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		intrans = false;
3297a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    }
3307a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
3317a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	autocommit = ac;
332417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
333417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
334417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public void setCatalog(String catalog) throws SQLException {
335417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
336417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
337417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public void setReadOnly(boolean ro) throws SQLException {
3387a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	if (intrans) {
3397a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    throw new SQLException("incomplete transaction");
3407a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
3417a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	if (ro != readonly) {
3427a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    DatabaseX dbx = null;
3437a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    try {
3447a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		dbx = open(ro);
3457a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		db.close();
3467a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		db = dbx;
3477a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		dbx = null;
3487a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		readonly = ro;
3497a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    } catch (SQLException e) {
3507a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		throw e;
3517a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    } catch (SQLite.Exception ee) {
3527a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		if (dbx != null) {
3537a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		    try {
3547a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes			dbx.close();
3557a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		    } catch (SQLite.Exception eee) {
3567a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		    }
3577a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		}
3587a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		throw new SQLException(ee.toString());
3597a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    }
3607a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
361417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
362417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
363417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public void setTransactionIsolation(int level) throws SQLException {
3647a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	if (db.is3() && SQLite.JDBCDriver.sharedCache) {
3657a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    String flag = null;
3667a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    if (level == TRANSACTION_READ_UNCOMMITTED &&
3677a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		trmode != TRANSACTION_READ_UNCOMMITTED) {
3687a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		flag = "on";
3697a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    } else if (level == TRANSACTION_SERIALIZABLE &&
3707a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		       trmode != TRANSACTION_SERIALIZABLE) {
3717a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		flag = "off";
3727a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    }
3737a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    if (flag != null) {
3747a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		try {
3757a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		    db.exec("PRAGMA read_uncommitted = " + flag + ";", null);
3767a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		    trmode = level;
3777a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		} catch (java.lang.Exception e) {
3787a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		}
3797a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    }
3807a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
3817a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	if (level != trmode) {
3827a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    throw new SQLException("not supported");
3837a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
384417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
385417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
386417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public java.util.Map<String, Class<?>> getTypeMap() throws SQLException {
38717c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	throw new SQLFeatureNotSupportedException();
388417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
389417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
390417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public void setTypeMap(java.util.Map map) throws SQLException {
39117c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	throw new SQLFeatureNotSupportedException();
392417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
393417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
394417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public int getHoldability() throws SQLException {
3957a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	return ResultSet.HOLD_CURSORS_OVER_COMMIT;
396417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
397417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
398417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public void setHoldability(int holdability) throws SQLException {
3997a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	if (holdability == ResultSet.HOLD_CURSORS_OVER_COMMIT) {
4007a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    return;
4017a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
40217c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	throw new SQLFeatureNotSupportedException("unsupported holdability");
403417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
404417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
405417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public Savepoint setSavepoint() throws SQLException {
40617c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	throw new SQLFeatureNotSupportedException();
407417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
408417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
409417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public Savepoint setSavepoint(String name) throws SQLException {
41017c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	throw new SQLFeatureNotSupportedException();
411417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
412417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
413417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public void rollback(Savepoint x) throws SQLException {
41417c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	throw new SQLFeatureNotSupportedException();
415417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
416417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
417417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public void releaseSavepoint(Savepoint x) throws SQLException {
41817c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	throw new SQLFeatureNotSupportedException();
419417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
420417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
421417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public Statement createStatement(int resultSetType,
4227a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes				     int resultSetConcurrency,
4237a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes				     int resultSetHoldability)
4247a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	throws SQLException {
4257a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	if (resultSetHoldability != ResultSet.HOLD_CURSORS_OVER_COMMIT) {
42617c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	    throw new SQLFeatureNotSupportedException("unsupported holdability");
4277a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
4287a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	return createStatement(resultSetType, resultSetConcurrency);
429417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
430417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
431417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public PreparedStatement prepareStatement(String sql, int resultSetType,
4327a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes					      int resultSetConcurrency,
4337a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes					      int resultSetHoldability)
4347a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	throws SQLException {
4357a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	if (resultSetHoldability != ResultSet.HOLD_CURSORS_OVER_COMMIT) {
43617c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	    throw new SQLFeatureNotSupportedException("unsupported holdability");
4377a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
4387a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	return prepareStatement(sql, resultSetType, resultSetConcurrency);
439417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
440417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
441417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public CallableStatement prepareCall(String sql, int x, int y, int z)
4427a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	throws SQLException {
44317c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	throw new SQLFeatureNotSupportedException();
444417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
445417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
446417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public PreparedStatement prepareStatement(String sql, int autokeys)
4477a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	throws SQLException {
4487a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	if (autokeys != Statement.NO_GENERATED_KEYS) {
44917c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	    throw new SQLFeatureNotSupportedException("generated keys not supported");
4507a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
4517a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	return prepareStatement(sql);
452417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
453417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
454417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public PreparedStatement prepareStatement(String sql, int colIndexes[])
4557a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	throws SQLException {
45617c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	throw new SQLFeatureNotSupportedException();
457417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
458417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
459417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public PreparedStatement prepareStatement(String sql, String columns[])
4607a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	throws SQLException {
46117c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	throw new SQLFeatureNotSupportedException();
46217c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe    }
46317c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe
46417c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe    public Clob createClob() throws SQLException {
46517c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	throw new SQLFeatureNotSupportedException();
46617c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe    }
46717c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe
46817c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe    public Blob createBlob() throws SQLException {
46917c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	throw new SQLFeatureNotSupportedException();
47017c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe    }
47117c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe
47217c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe    public NClob createNClob() throws SQLException {
47317c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	throw new SQLFeatureNotSupportedException();
47417c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe    }
47517c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe
47617c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe    public SQLXML createSQLXML() throws SQLException {
47717c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	throw new SQLFeatureNotSupportedException();
47817c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe    }
47917c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe
48017c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe    public boolean isValid(int timeout) throws SQLException {
48117c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe        return true;
48217c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe    }
48317c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe
48417c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe    public void setClientInfo(String name, String value)
48517c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	throws SQLClientInfoException {
48617c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	throw new SQLClientInfoException();
48717c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe    }
48817c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe
48917c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe    public void setClientInfo(Properties prop) throws SQLClientInfoException {
49017c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	throw new SQLClientInfoException();
49117c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe    }
49217c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe
49317c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe    public String getClientInfo(String name) throws SQLException {
49417c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	throw new SQLException("unsupported");
49517c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe    }
49617c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe
49717c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe    public Properties getClientInfo() throws SQLException {
49817c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe        return new Properties();
49917c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe    }
50017c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe
50117c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe    public Array createArrayOf(String type, Object[] elems)
50217c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe 	throws SQLException {
50317c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	throw new SQLFeatureNotSupportedException();
50417c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe    }
50517c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe
50617c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe    public Struct createStruct(String type, Object[] attrs)
50717c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	throws SQLException {
50817c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	throw new SQLFeatureNotSupportedException();
50917c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe    }
51017c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe
51117c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe    public <T> T unwrap(java.lang.Class<T> iface) throws SQLException {
51217c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	throw new SQLException("unsupported");
51317c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe    }
51417c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe
51517c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe    public boolean isWrapperFor(java.lang.Class iface) throws SQLException {
51617c83b1a74c906c9a36257a3a99cd1e3730b002eJeremy Sharpe	return false;
517417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
518417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
519417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes}
520417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
521417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughesclass DatabaseX extends SQLite.Database {
522417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
523417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    static Object lock = new Object();
524417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
525417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public DatabaseX() {
5267a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	super();
527417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
528417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
529417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    void wait(int ms) {
5307a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	try {
5317a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    synchronized (lock) {
5327a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes		lock.wait(ms);
5337a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    }
5347a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	} catch (java.lang.Exception e) {
5357a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
536417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
537417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
538417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public void exec(String sql, SQLite.Callback cb)
5397a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	throws SQLite.Exception {
5407a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	super.exec(sql, cb);
5417a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	synchronized (lock) {
5427a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    lock.notifyAll();
5437a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
544417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
545417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
546417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public void exec(String sql, SQLite.Callback cb, String args[])
5477a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	throws SQLite.Exception {
5487a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	super.exec(sql, cb, args);
5497a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	synchronized (lock) {
5507a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    lock.notifyAll();
5517a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
552417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
553417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
554417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public SQLite.TableResult get_table(String sql, String args[])
5557a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	throws SQLite.Exception {
5567a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	SQLite.TableResult ret = super.get_table(sql, args);
5577a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	synchronized (lock) {
5587a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    lock.notifyAll();
5597a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
5607a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	return ret;
561417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
562417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
563417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    public void get_table(String sql, String args[], SQLite.TableResult tbl)
5647a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	throws SQLite.Exception {
5657a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	super.get_table(sql, args, tbl);
5667a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	synchronized (lock) {
5677a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	    lock.notifyAll();
5687a647e8547e57ca573541be55b3728ef7ce376feElliott Hughes	}
569417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes    }
570417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes
571417deb1db112103aff04231b6ca79772ff7d3a21Elliott Hughes}
572