⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 main.c

📁 Gambas is a graphical development environment based on a Basic interpreter, like Visual Basic. It us
💻 C
📖 第 1 页 / 共 4 页
字号:
/*****************************************************************************  query_fill()  Fill a result buffer with the value of each field of a record.  <result> is the handle of the result.  <pos> is the index of the record in the result.  <buffer> points to an array having one element for each field in the  result.  <next> is a boolean telling if we want the next row.  This function must use GB.StoreVariant() to store the value in the  buffer.*****************************************************************************/static void query_fill(DB_RESULT result, int pos, GB_VARIANT_VALUE *buffer, int next){  MYSQL_RES *res = (MYSQL_RES *)result;  MYSQL_FIELD *field;  MYSQL_ROW row;  int i;  char *data;  GB_VARIANT value;  if (!next)    mysql_data_seek(res, pos);/* move to record */  row = mysql_fetch_row(res);  mysql_field_seek(res, 0);  for ( i=0; i < mysql_num_fields(res); i++)  {        field = mysql_fetch_field(res);       data = row[i];        value.type = GB_T_VARIANT;        value.value._object.type = GB_T_NULL;        //if (field->type != FIELD_TYPE_NULL)        if (data){            conv_data(data, &value.value, field->type, field->length);        }        GB.StoreVariant(&value, &buffer[i]);  }}/*****************************************************************************  field_name()  Return the name of a field in a result from its index.  <result> is the result handle.  <field> is the field index.*****************************************************************************/static char *field_name(DB_RESULT result, int field){	MYSQL_FIELD *fld;	int i, num_fields = mysql_num_fields((MYSQL_RES *)result);	char *table1 = mysql_fetch_field_direct((MYSQL_RES *)result, 0)->table;	bool MultiTables = FALSE;	// Need to identify whether multiple tables included        fld = mysql_fetch_fields((MYSQL_RES *)result);        for ( i = 1; i < num_fields; i++ ){		if (strcmp(table1, fld[i].table) != 0){			MultiTables = TRUE;			break;		}	}        fld = mysql_fetch_field_direct((MYSQL_RES *)result, field);	// GB.Alloc((void **)&full, strlen(fld->table) + strlen(fld->name));	if (MultiTables && *fld->table){	   sprintf(_buffer, "%s.%s", fld->table, fld->name);	   return _buffer;	}	else {		return fld->name;	}  //return mysql_fetch_field_direct((MYSQL_RES *)result, field)->name;}/*****************************************************************************  field_index()  Return the index of a field in a result from its name.  <Result> is the result handle.  <name> is the field name.*****************************************************************************/static int field_index(DB_RESULT Result, char *name, DB_DATABASE handle, long version){  unsigned int num_fields;  unsigned int i;  MYSQL_FIELD *field;  //char *table = NULL, *fld = NULL;  char *table, *fld;  MYSQL_RES *result = (MYSQL_RES *)Result;  fld = strchr(name, (int)FLD_SEP);  if (fld){ /* Field does includes table info */       GB.NewString(&table, name, fld - name);       fld = fld + 1;  }  else {          table = NULL;	  fld = name;  }  num_fields = mysql_num_fields(result);  if (strcmp(name,fld)!=0){ /* table name included */     mysql_field_seek(result,0); /* start at beginning */     for (i = 0; i < num_fields; i++)     {         field = mysql_fetch_field(result);	 if ( strcasecmp( fld, field->name) == 0 && strcmp( table, field->table) == 0){	     GB.FreeString(&table); return i;	 }     }     fld = name;  }  if (table)     GB.FreeString(&table);  /* Do not consider table name, also reached where table cannot be found. *   * Mysql can include . in the fieldname!!                                */  mysql_field_seek(result,0); /* start at beginning */  for (i = 0; i < num_fields; i++)  {      field = mysql_fetch_field(result);      if ( strcasecmp( fld, field->name) == 0)          return i;  }  return -1;}/*****************************************************************************  field_type()  Return the Gambas type of a field in a result from its index.  <result> is the result handle.  <field> is the field index.*****************************************************************************/static GB_TYPE field_type(DB_RESULT result, int field){  MYSQL_FIELD *f = mysql_fetch_field_direct((MYSQL_RES *)result, field);  return conv_type(f->type, f->length);}/*****************************************************************************  field_length()  Return the length of a field in a result from its index.  <result> is the result handle.  <field> is the field index.*****************************************************************************/static int field_length(DB_RESULT result, int field){  MYSQL_FIELD *f = mysql_fetch_field_direct((MYSQL_RES *)result, field);  GB_TYPE type = conv_type(f->type, f->length);  if (type != GB_T_STRING)    return 0;  else    return f->length;}/*****************************************************************************  begin_transaction()  Begin a transaction.  <handle> is the database handle.  This function returns TRUE if the command has failed, and FALSE if  everything was OK.  In mysql commit/rollback can only be used with transaction safe tables (BDB,  or InnoDB tables)  ISAM, MyISAM and HEAP tables will commit straight away. The transaction  methods are therefore ignored.*****************************************************************************/static int begin_transaction(DB_DATABASE handle){  /* Autocommit is on by default. Lets set it off. */  /* BM: why not doing that when we open the connection ? */  do_query((MYSQL *)handle, "Unable to set autocommit to 0: &1", NULL, "set autocommit=0", 0);  return do_query((MYSQL *)handle, "Unable to begin transaction: &1", NULL, "BEGIN", 0);}/*****************************************************************************  commit_transaction()  Commit a transaction.  <handle> is the database handle.  This function returns TRUE if the command has failed, and FALSE if  everything was OK.*****************************************************************************/static int commit_transaction(DB_DATABASE handle){  bool ret = do_query((MYSQL *)handle, "Unable to commit transaction: &1", NULL, "COMMIT", 0);  /* Autocommit needs to be set back on. */  /* BM: and what happens if transactions are imbricated ? */  do_query((MYSQL *)handle, "Unable to set autocommit to On: &1", NULL, "set autocommit=1", 0);  return ret;}/*****************************************************************************  rollback_transaction()  Rollback a transaction.  <handle> is the database handle.  This function returns TRUE if the command has failed, and FALSE if  everything was OK.  In mysql commit/rollback can only be used with transaction safe tables (BDB,  or InnoDB tables)  ISAM, MyISAM and HEAP tables will commit straight away. Therefore a rollback  cannot occur!*****************************************************************************/static int rollback_transaction(DB_DATABASE handle){  bool ret = do_query((MYSQL *)handle, "Unable to rollback transaction: &1", NULL, "ROLLBACK", 0);  /* Autocommit needs to be set back on. */  /* BM: and what happens if transactions are imbricated ? */  do_query((MYSQL *)handle, "Unable to set autocommit to On: &1", NULL, "set autocommit=1", 0);  return ret;}/*****************************************************************************  table_init()  Initialize an info structure from table fields.  <handle> is the database handle.  <table> is the table name.  <info> points at the info structure.  This function must initialize the following info fields:   - info->nfield must contain the number of fields in the table.   - info->fields is a char*[] pointing at the name of each field.   - info->types is a GB_TYPE[] giving the gambas type of each field.  This function returns TRUE if the command has failed, and FALSE if  everything was OK.*****************************************************************************/static int table_init(DB_DATABASE db, char *table, DB_INFO *info){  MYSQL_FIELD *field;  MYSQL *conn = (MYSQL *)db;  MYSQL_RES *res;  int i, n;  DB_FIELD *f;  /* Nom de la table */  GB.NewString(&info->table, table, 0);  res = mysql_list_fields( conn, table, 0);  if (!res)    return TRUE;  info->nfield = n = mysql_num_fields(res);  if (n == 0)    return TRUE;  GB.Alloc((void **)&info->field, sizeof(DB_FIELD) * n);  i = 0;  while ((field = mysql_fetch_field(res)))  {    f = &info->field[i];    GB.NewString(&f->name, field->name, 0);    f->type = conv_type(field->type, field->length);    f->length = 0;    if (f->type == GB_T_STRING)      f->length = field->length;    i++;  }  mysql_free_result(res);  return FALSE;}/*****************************************************************************  table_index()  Initialize an info structure from table primary index.  <handle> is the database handle.  <table> is the table name.  <info> points at the info structure.  This function must initialize the following info fields:   - info->nindex must contain the number of fields in the primary index.   - info->index is a int[] giving the index of each index field in     info->fields.  This function must be called after table_init().  This function returns TRUE if the command has failed, and FALSE if  everything was OK.*****************************************************************************/static int table_index(DB_DATABASE db, char *table, DB_INFO *info){  char *qindex =    "show index from `&1`";  MYSQL *conn = (MYSQL *)db;  MYSQL_RES *res;  MYSQL_ROW row;  int i, j, n;  /* Index primaire */  if (do_query(conn, "Unable to get primary index: &1", &res, qindex, 1, table))	  return TRUE;  for ( i = 0, n = 0;  i < mysql_num_rows(res); i++ )  {    row = mysql_fetch_row(res);    if (strcmp("PRIMARY", row[2]) == 0) /* Use only Primary key */	    n++;  }  mysql_data_seek(res, 0);/* move back to first record */  info->nindex = n;  /* Note: Col 3 is Key_name, Col 4 is Sq_in_index, Col 5 is Field Name */  if (n <= 0)  {    GB.Error("Table '&1' has no primary index", table);    return TRUE;  }  GB.Alloc((void **)&info->index, sizeof(int) * n);  for (i = 0; i < n; i++)  {    row = mysql_fetch_row(res);    if (strcmp("PRIMARY", row[2]) == 0) /* Use only Primary key */    {        for (j = 0; j < info->nfield; j++)        {            if (strcasecmp(info->field[j].name,  row[4]) == 0)            {                info->index[i] = j;                break;            }     	 }    }  }  mysql_free_result(res);  return FALSE;}/*****************************************************************************  table_release()  Free the info structure filled by table_init() and/or table_index()  <handle> is the database handle.  <info> points at the info structure.*****************************************************************************/static void table_release(DB_DATABASE db, DB_INFO *info){  /* All is done outside the driver */}/*****************************************************************************  table_exist()  Returns if a table exists  <handle> is the database handle.  <table> is the table name.  This function returns TRUE if the table exists, and FALSE if not.*****************************************************************************/static int table_exist(DB_DATABASE handle, char *table){  MYSQL *conn = (MYSQL *)handle;  MYSQL_RES *res;  int exist;  const char *query =    "show tables like '&1'";  if (do_query(conn, "Unable to check table: &1", &res, query, 1, table))    return FALSE;  exist = mysql_num_rows(res);  mysql_free_result(res);  //return FALSE;  return exist;}/*****************************************************************************  table_list()  Returns an array containing the name of each table in the database  <handle> is the database handle.  <tables> points to a variable that will receive the char* array.  This function returns the number of tables, or -1 if the command has  failed.  Be careful: <tables> can be NULL, so that just the count is returned.*****************************************************************************/static long table_list(DB_DATABASE handle, char ***tables, long version){  MYSQL *conn = (MYSQL *)handle;  MYSQL_RES *res;  MYSQL_ROW row;  long i;  long rows;  const char *query =    "show tables";  if (do_query(conn, "Unable to get tables", &res, query, 0))    return -1;  rows = mysql_num_rows(res);  GB.NewArray(tables, sizeof(char *), rows);  for (i = 0; i < rows; i++){    row = mysql_fetch_row(res);    GB.NewString(&(*tables)[i], row[0], 0);  }  mysql_free_result(res);  return rows;}/*****************************************************************************  table_primary_key()  Returns a string representing the primary key of a table.  <handle> is the database handle.  <table> is the table name.  <key> points to a string that will receive the primary key.  This function returns TRUE if the command has failed, and FALSE if  everything was OK.*****************************************************************************/static int table_primary_key(DB_DATABASE handle, char *table, char ***primary){  const char *query =    "show index from `&1`";  MYSQL *conn = (MYSQL *)handle;  MYSQL_RES *res;  MYSQL_ROW row;  int i;  if (do_query(conn, "Unable to get primary key: &1", &res, query, 1, table))    return TRUE;  GB.NewArray(primary, sizeof(char *), 0);  for (i = 0; i < mysql_num_rows(res); i++)  {    row = mysql_fetch_row(res);    if (strcmp("PRIMARY", row[2]) == 0)      GB.NewString((char **)GB.Add(primary), row[4], 0);  }  mysql_free_result(res);  return FALSE;}/*****************************************************************************  table_is_system()  Returns if a table is a system table.  <handle> is the database handle.  <table> is the table name.  This function returns TRUE if the table is a system table, and FALSE if  not.  Note: In mysql the system tables are stored in a separate database.  The tables are mysql.columns_priv, mysql.db, mysql.func, mysql.host,  mysql.tables_priv, mysql.user. This has therefore not been implemented.*****************************************************************************/static int table_is_system(DB_DATABASE handle, char *table, long version){  const char *query =      "select database()";  MYSQL *conn = (MYSQL *)handle;  MYSQL_RES *res;  MYSQL_ROW row;  int system;  if (do_query(conn, "Unable to check database: &1", &res, query, 0))    return FALSE;  if (mysql_num_rows(res) != 1 ){    GB.Error("Unable to check database: More than one database returned !?");    return FALSE;  }  /* (BM) Check that the current database is mysql */  row = mysql_fetch_row(res);  if (strcmp(row[0], "mysql"))    system = FALSE;  else  {    if (strcmp(table, "columns_priv") == 0        || strcmp(table, "db") == 0        || strcmp(table, "func") == 0        || strcmp(table, "host") == 0        || strcmp(table, "tables_priv") == 0

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -