📄 localcli.cpp
字号:
int dbCLI::free_statement(int statement)
{
statement_desc* stmt = statements.get(statement);
if (stmt == NULL) {
return cli_bad_descriptor;
}
return free_statement(stmt);
}
int dbCLI::free_statement(statement_desc* stmt)
{
{
dbCriticalSection cs(stmt->session->mutex);
statement_desc *sp, **spp = &stmt->session->stmts;
while ((sp = *spp) != stmt) {
if (sp == NULL) {
return cli_bad_descriptor;
}
spp = &sp->next;
}
*spp = stmt->next;
}
return release_statement(stmt);
}
int dbCLI::release_statement(statement_desc* stmt)
{
column_binding *cb, *next_cb;
for (cb = stmt->columns; cb != NULL; cb = next_cb) {
next_cb = cb->next;
delete[] cb->name;
column_allocator.free(cb);
}
parameter_binding *pb, *next_pb;
for (pb = stmt->params; pb != NULL; pb = next_pb) {
next_pb = pb->next;
delete[] pb->name;
parameter_allocator.free(pb);
}
if (stmt->cursor.db != NULL) {
stmt->cursor.reset();
stmt->cursor.deallocateBitmap();
}
statements.free(stmt);
return cli_ok;
}
int cli_commit(int session)
{
return dbCLI::instance.commit(session);
}
int dbCLI::commit(int session)
{
session_desc* s = sessions.get(session);
if (s == NULL) {
return cli_bad_descriptor;
}
while (s->dropped_tables != NULL) {
dbTableDescriptor* next = s->dropped_tables->nextDbTable;
delete s->dropped_tables;
s->dropped_tables = next;
}
s->db->commit();
s->existed_tables = s->db->tables;
return cli_ok;
}
int cli_precommit(int session)
{
return dbCLI::instance.precommit(session);
}
int dbCLI::precommit(int session)
{
session_desc* s = sessions.get(session);
if (s == NULL) {
return cli_bad_descriptor;
}
s->db->precommit();
return cli_ok;
}
int cli_abort(int session)
{
return dbCLI::instance.abort(session);
}
int dbCLI::abort(int session)
{
session_desc* s = sessions.get(session);
if (s == NULL) {
return cli_bad_descriptor;
}
dbDatabase* db = s->db;
while (s->dropped_tables != NULL) {
dbTableDescriptor* next = s->dropped_tables->nextDbTable;
db->linkTable(s->dropped_tables, s->dropped_tables->tableId);
s->dropped_tables = next;
}
s->db->rollback();
while (db->tables != s->existed_tables) {
dbTableDescriptor* table = db->tables;
db->unlinkTable(table);
delete table;
}
return cli_ok;
}
int cli_remove(int statement)
{
return dbCLI::instance.remove(statement);
}
int dbCLI::remove(int statement)
{
statement_desc* stmt = statements.get(statement);
if (stmt == NULL || !stmt->prepared) {
return cli_bad_descriptor;
}
if (!stmt->for_update) {
return cli_not_update_mode;
}
if (stmt->cursor.isEmpty()) {
return cli_not_found;
}
stmt->cursor.removeAllSelected();
return cli_ok;
}
int cli_describe(int session, char const* table, cli_field_descriptor** fields)
{
return dbCLI::instance.describe(session, table, fields);
}
int dbCLI::describe(int session, char const* table, cli_field_descriptor** fields)
{
session_desc* s = sessions.get(session);
if (s == NULL) {
return cli_bad_descriptor;
}
dbDatabase* db = s->db;
dbTableDescriptor* desc = db->findTableByName(table);
if (desc == NULL) {
return cli_table_not_found;
} else {
int nColumns = desc->nColumns;
cli_field_descriptor* fp =
(cli_field_descriptor*)malloc(nColumns*sizeof(cli_field_descriptor));
dbFieldDescriptor* fd = desc->columns;
*fields = fp;
for (int i = 0; i < nColumns; i++, fp++) {
fp->type = (cli_var_type)map_type(fd);
fp->name = fd->name;
fp->refTableName = (fd->type == dbField::tpArray) ? fd->components->refTableName : fd->refTableName;
fp->inverseRefFieldName = fd->inverseRefName;
fp->flags = fd->indexType;
if (fd->tTree != 0) {
fp->flags |= cli_indexed;
}
if (fd->hashTable != 0) {
fp->flags |= cli_hashed;
}
fd = fd->next;
}
return nColumns;
}
}
int cli_describe_layout(int session, char const* table, cli_field_layout** fields, int* rec_size)
{
return dbCLI::instance.describe_layout(session, table, fields, rec_size);
}
int dbCLI::describe_layout(int session, char const* table, cli_field_layout** fields, int* rec_size)
{
session_desc* s = sessions.get(session);
if (s == NULL) {
return cli_bad_descriptor;
}
dbDatabase* db = s->db;
dbTableDescriptor* desc = db->findTableByName(table);
if (desc == NULL) {
return cli_table_not_found;
} else {
int nColumns = desc->nColumns;
cli_field_layout* fp =
(cli_field_layout*)malloc(nColumns*sizeof(cli_field_layout));
dbFieldDescriptor* fd = desc->columns;
*fields = fp;
*rec_size = desc->appSize;
for (int i = 0; i < nColumns; i++, fp++) {
fp->desc.type = (cli_var_type)map_type(fd);
fp->desc.name = fd->name;
fp->desc.refTableName = (fd->type == dbField::tpArray) ? fd->components->refTableName : fd->refTableName;
fp->desc.inverseRefFieldName = fd->inverseRefName;
fp->desc.flags = fd->indexType;
if (fd->tTree != 0) {
fp->desc.flags |= cli_indexed;
}
if (fd->hashTable != 0) {
fp->desc.flags |= cli_hashed;
}
fp->offs = fd->appOffs;
fp->size = fd->appSize;
fd = fd->next;
}
return nColumns;
}
}
int cli_show_tables(int session, cli_table_descriptor** tables)
{
return dbCLI::instance.show_tables(session, tables);
}
int dbCLI::show_tables(int session, cli_table_descriptor** tables)
{
session_desc* s = sessions.get(session);
if (s == NULL) {
return cli_bad_descriptor;
}
dbTableDescriptor* desc;
int nTables = 0;
for (desc = s->db->tables; desc != NULL; desc = desc->nextDbTable) {
if (strcmp(desc->name, "Metatable")) {
nTables += 1;
}
}
if (nTables != 0) {
cli_table_descriptor* td = (cli_table_descriptor*)malloc(nTables*sizeof(cli_table_descriptor));
*tables = td;
for (desc = s->db->tables; desc != NULL; desc = desc->nextDbTable) {
if (strcmp(desc->name, "Metatable")) {
td->name = desc->name;
td += 1;
}
}
} else {
*tables = NULL;
}
return nTables;
}
#define MAX_QUERY_IDENTIFIER_LENGTH 256
int sql_scanner::get()
{
char buf[MAX_QUERY_IDENTIFIER_LENGTH];
int i = 0, ch;
do {
ch = *p++;
if (ch == '\0') {
return tkn_eof;
}
} while (ch > 0 && ch <= 32);
if (ch == '*') {
return tkn_all;
} else if ((ch >= '0' && ch <= '9') || ch == '+' || ch == '-') {
int const_type = tkn_iconst;
while (true) {
ch = *p++;
if (ch == '.' || ch == 'e' || ch == 'E') {
const_type = tkn_fconst;
} else if (!((ch >= '0' && ch <= '9') || ch == '+' || ch == '-')) {
break;
}
}
return const_type;
} else if (isalnum(ch) || ch == '$' || ch == '_') {
do {
buf[i++] = ch;
if (i == MAX_QUERY_IDENTIFIER_LENGTH) {
// Identifier too long
return tkn_error;
}
ch = *p++;
} while (ch != EOF && (isalnum(ch) || ch == '$' || ch == '_'));
p -= 1;
buf[i] = '\0';
ident = buf;
return dbSymbolTable::add(ident, tkn_ident);
} else {
// Invalid symbol
return tkn_error;
}
}
int cli_create_table(int session, char const* tableName, int nColumns,
cli_field_descriptor* columns)
{
return dbCLI::instance.create_table(session, tableName, nColumns, columns);
}
int cli_alter_table(int session, char const* tableName, int nColumns,
cli_field_descriptor* columns)
{
return dbCLI::instance.alter_table(session, tableName, nColumns, columns);
}
int dbCLI::create_table(int session, char const* tableName, int nColumns,
cli_field_descriptor* columns)
{
session_desc* s = sessions.get(session);
if (s == NULL) {
return cli_bad_descriptor;
}
s->db->beginTransaction(dbDatabase::dbExclusiveLock);
if (s->existed_tables == NULL) {
s->existed_tables = s->db->tables;
}
return create_table(s->db, tableName, nColumns, columns);
}
int dbCLI::alter_table(int session, char const* tableName, int nColumns,
cli_field_descriptor* columns)
{
session_desc* s = sessions.get(session);
if (s == NULL) {
return cli_bad_descriptor;
}
s->db->beginTransaction(dbDatabase::dbExclusiveLock);
return alter_table(s->db, tableName, nColumns, columns);
}
int dbCLI::calculate_varying_length(char const* tableName, int& nFields, cli_field_descriptor* columns)
{
int varyingLength = strlen(tableName) + 1;
for (int i = 0, n = nFields; i < n; i++) {
int type = columns[i].type;
varyingLength += strlen(columns[i].name) + 3;
if (type == cli_oid || type == cli_array_of_oid) {
varyingLength += strlen(columns[i].refTableName);
if (columns[i].inverseRefFieldName != NULL) {
varyingLength += strlen(columns[i].inverseRefFieldName);
}
}
switch (type) {
case cli_oid:
case cli_bool:
case cli_int1:
case cli_int2:
case cli_int4:
case cli_autoincrement:
case cli_int8:
case cli_real4:
case cli_real8:
case cli_asciiz:
case cli_pasciiz:
case cli_datetime:
case cli_rectangle:
break;
case cli_array_of_oid:
case cli_array_of_bool:
case cli_array_of_int1:
case cli_array_of_int2:
case cli_array_of_int4:
case cli_array_of_int8:
case cli_array_of_real4:
case cli_array_of_real8:
case cli_array_of_string:
varyingLength += strlen(columns[i].name) + 2 + 3;
nFields += 1;
break;
case cli_unknown:
return cli_unsupported_type;
}
}
return varyingLength;
}
dbTableDescriptor* dbCLI::create_table_descriptor(dbDatabase* db,
oid_t oid,
dbTable* table,
char const* tableName,
int nFields,
int nC
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -