List:Commits« Previous MessageNext Message »
From:Patrick Galbraith Date:January 30 2006 11:15pm
Subject:bk commit into 5.1 tree (patg:1.2047)
View as plain text  
Below is the list of changes that have just been committed into a local
5.1 repository of patg. When patg does a push these changes will
be propagated to the main repository and, within 24 hours after the
push, to the public repository.
For information on how to access the public repository
see http://dev.mysql.com/doc/mysql/en/installing-source-tree.html

ChangeSet
  1.2047 06/01/30 15:14:56 patg@stripped +14 -0
  WL# 3031
  
  This is a work in progress, not at all ready for any sort of review!

  sql/sql_connections.h
    1.1 06/01/30 15:07:02 patg@stripped +37 -0
    WL# 3031
    
    This is a work in progress, not at all ready for any sort of review!
    

  sql/sql_connections.h
    1.0 06/01/30 15:07:02 patg@stripped +0 -0
    BitKeeper file /home/patg/mysql-build/mysql-5.1-new/sql/sql_connections.h

  sql/sql_connections.cc
    1.1 06/01/30 15:07:01 patg@stripped +319 -0
    WL# 3031
    
    This is a work in progress, not at all ready for any sort of review!
    

  sql/sql_connections.cc
    1.0 06/01/30 15:07:01 patg@stripped +0 -0
    BitKeeper file /home/patg/mysql-build/mysql-5.1-new/sql/sql_connections.cc

  libmysqld/sql_connections.cc
    1.1 06/01/30 15:07:00 patg@stripped +0 -0
    WL# 3031
    
    This is a work in progress, not at all ready for any sort of review!
    

  sql/sql_yacc.yy
    1.436 06/01/30 15:07:00 patg@stripped +58 -0
    WL# 3031
    
    This is a work in progress, not at all ready for any sort of review!

  libmysqld/sql_connections.cc
    1.0 06/01/30 15:07:00 patg@stripped +0 -0
    BitKeeper file /home/patg/mysql-build/mysql-5.1-new/libmysqld/sql_connections.cc

  sql/sql_parse.cc
    1.503 06/01/30 15:06:59 patg@stripped +12 -0
    WL# 3031
    
    This is a work in progress, not at all ready for any sort of review!

  sql/sql_lex.h
    1.214 06/01/30 15:06:59 patg@stripped +9 -1
    WL# 3031
    
    This is a work in progress, not at all ready for any sort of review!

  sql/share/errmsg.txt
    1.66 06/01/30 15:06:59 patg@stripped +3 -0
    WL# 3031
    
    This is a work in progress, not at all ready for any sort of review!

  sql/mysqld.cc
    1.513 06/01/30 15:06:59 patg@stripped +4 -0
    WL# 3031
    
    This is a work in progress, not at all ready for any sort of review!

  sql/mysql_priv.h
    1.363 06/01/30 15:06:59 patg@stripped +1 -0
    WL# 3031
    
    This is a work in progress, not at all ready for any sort of review!

  sql/lex.h
    1.149 06/01/30 15:06:59 patg@stripped +7 -0
    WL# 3031
    
    This is a work in progress, not at all ready for any sort of review!

  sql/ha_federated.h
    1.26 06/01/30 15:06:59 patg@stripped +3 -1
    WL# 3031
    
    This is a work in progress, not at all ready for any sort of review!

  sql/ha_federated.cc
    1.47 06/01/30 15:06:59 patg@stripped +201 -78
    WL# 3031
    
    This is a work in progress, not at all ready for any sort of review!

  sql/Makefile.am
    1.130 06/01/30 15:06:59 patg@stripped +4 -2
    WL# 3031
    
    This is a work in progress, not at all ready for any sort of review!

  libmysqld/Makefile.am
    1.77 06/01/30 15:06:58 patg@stripped +2 -1
    WL# 3031
    
    This is work in progress, not at all ready for any sort of review!

# This is a BitKeeper patch.  What follows are the unified diffs for the
# set of deltas contained in the patch.  The rest of the patch, the part
# that BitKeeper cares about, is below these diffs.
# User:	patg
# Host:	krsna.patg.net
# Root:	/home/patg/mysql-build/mysql-5.1-new

--- 1.129/sql/Makefile.am	2005-12-31 01:13:33 -08:00
+++ 1.130/sql/Makefile.am	2006-01-30 15:06:59 -08:00
@@ -64,7 +64,8 @@
 			sp_head.h sp_pcontext.h sp_rcontext.h sp.h sp_cache.h \
 			parse_file.h sql_view.h	sql_trigger.h \
 			sql_array.h sql_cursor.h \
-			sql_plugin.h authors.h
+			sql_plugin.h authors.h \
+			sql_connections.h
 mysqld_SOURCES =	sql_lex.cc sql_handler.cc sql_partition.cc \
 			item.cc item_sum.cc item_buff.cc item_func.cc \
 			item_cmpfunc.cc item_strfunc.cc item_timefunc.cc \
@@ -98,7 +99,8 @@
 			sp_head.cc sp_pcontext.cc  sp_rcontext.cc sp.cc \
 			sp_cache.cc parse_file.cc sql_trigger.cc \
 			sql_plugin.cc sql_binlog.cc \
-			handlerton.cc
+			handlerton.cc \
+			sql_connections.cc
 EXTRA_mysqld_SOURCES =	ha_innodb.cc ha_berkeley.cc ha_archive.cc \
 			ha_innodb.h  ha_berkeley.h  ha_archive.h \
 			ha_blackhole.cc ha_federated.cc ha_ndbcluster.cc \

--- 1.148/sql/lex.h	2005-12-21 05:09:01 -08:00
+++ 1.149/sql/lex.h	2006-01-30 15:06:59 -08:00
@@ -228,6 +228,7 @@
   { "HAVING",		SYM(HAVING)},
   { "HELP",		SYM(HELP_SYM)},
   { "HIGH_PRIORITY",	SYM(HIGH_PRIORITY)},
+  { "HOST",		SYM(HOST_SYM)},
   { "HOSTS",		SYM(HOSTS_SYM)},
   { "HOUR",		SYM(HOUR_SYM)},
   { "HOUR_MICROSECOND",	SYM(HOUR_MICROSECOND_SYM)},
@@ -365,6 +366,7 @@
   { "ONE_SHOT",		SYM(ONE_SHOT_SYM)},
   { "OPEN",		SYM(OPEN_SYM)},
   { "OPTIMIZE",		SYM(OPTIMIZE)},
+  { "OPTIONS",		SYM(OPTIONS_SYM)},
   { "OPTION",		SYM(OPTION)},
   { "OPTIONALLY",	SYM(OPTIONALLY)},
   { "OR",		SYM(OR_SYM)},
@@ -372,6 +374,7 @@
   { "OUT",              SYM(OUT_SYM)},
   { "OUTER",		SYM(OUTER)},
   { "OUTFILE",		SYM(OUTFILE)},
+  { "OWNER",		SYM(OWNER_SYM)},
   { "PACK_KEYS",	SYM(PACK_KEYS_SYM)},
   { "PARSER",           SYM(PARSER_SYM)},
   { "PARTIAL",		SYM(PARTIAL)},
@@ -382,6 +385,7 @@
   { "PLUGIN",           SYM(PLUGIN_SYM)},
   { "POINT",		SYM(POINT_SYM)},
   { "POLYGON",		SYM(POLYGON)},
+  { "PORT",		SYM(PORT_SYM)},
   { "PRECISION",	SYM(PRECISION)},
   { "PREPARE",          SYM(PREPARE_SYM)},
   { "PREV",		SYM(PREV_SYM)},
@@ -447,6 +451,7 @@
   { "SERIAL",		SYM(SERIAL_SYM)},
   { "SERIALIZABLE",	SYM(SERIALIZABLE_SYM)},
   { "SESSION",		SYM(SESSION_SYM)},
+  { "SERVER",           SYM(SERVER_SYM)},
   { "SET",		SYM(SET)},
   { "SHARE",		SYM(SHARE_SYM)},
   { "SHOW",		SYM(SHOW)},
@@ -456,6 +461,7 @@
   { "SLAVE",            SYM(SLAVE)},
   { "SNAPSHOT",         SYM(SNAPSHOT_SYM)},
   { "SMALLINT",		SYM(SMALLINT)},
+  { "SOCKET",		SYM(SOCKET_SYM)},
   { "SOME",             SYM(ANY_SYM)},
   { "SONAME",		SYM(SONAME_SYM)},
   { "SOUNDS",		SYM(SOUNDS_SYM)},
@@ -556,6 +562,7 @@
   { "VIEW",		SYM(VIEW_SYM)},
   { "WITH",		SYM(WITH)},
   { "WORK",		SYM(WORK_SYM)},
+  { "WRAPPER",		SYM(WRAPPER_SYM)},
   { "WRITE",		SYM(WRITE_SYM)},
   { "X509",		SYM(X509_SYM)},
   { "XOR",		SYM(XOR)},

--- 1.362/sql/mysql_priv.h	2005-12-31 00:23:08 -08:00
+++ 1.363/sql/mysql_priv.h	2006-01-30 15:06:59 -08:00
@@ -547,6 +547,7 @@
 #include "sql_acl.h"
 #include "tztime.h"
 #include "opt_range.h"
+#include "sql_connections.h"
 
 #ifdef HAVE_QUERY_CACHE
 struct Query_cache_query_flags

--- 1.512/sql/mysqld.cc	2006-01-05 01:54:09 -08:00
+++ 1.513/sql/mysqld.cc	2006-01-30 15:06:59 -08:00
@@ -1142,6 +1142,7 @@
   my_tz_free();
   my_dbopt_free();
 #ifndef NO_EMBEDDED_ACCESS_CHECKS
+  connections_free(1);
   acl_free(1);
   grant_free();
 #endif
@@ -3568,6 +3569,9 @@
   if (!opt_noacl)
     (void) grant_init();
 
+  if (connections_init(0))
+  {
+  }
   if (!opt_noacl)
   {
     plugin_load();

--- 1.213/sql/sql_lex.h	2005-12-26 03:53:40 -08:00
+++ 1.214/sql/sql_lex.h	2006-01-30 15:06:59 -08:00
@@ -94,7 +94,7 @@
   SQLCOM_SHOW_PROC_CODE, SQLCOM_SHOW_FUNC_CODE,
   SQLCOM_INSTALL_PLUGIN, SQLCOM_UNINSTALL_PLUGIN,
   SQLCOM_SHOW_AUTHORS, SQLCOM_BINLOG_BASE64_EVENT,
-  SQLCOM_SHOW_PLUGINS,
+  SQLCOM_SHOW_PLUGINS, SQLCOM_CREATE_SERVER,
   /* This should be the last !!! */
 
   SQLCOM_END
@@ -153,6 +153,13 @@
 
 typedef List<Item> List_item;
 
+/* CONNECTION CACHE CHANGES */
+typedef struct st_lex_connection_options
+{
+  ulong port;
+  char *server_name, *host, *username, *password, *scheme, *socket, *owner;
+} LEX_CONNECTION_OPTIONS;
+
 typedef struct st_lex_master_info
 {
   char *host, *user, *password, *log_file_name;
@@ -807,6 +814,7 @@
   HA_CHECK_OPT   check_opt;			// check/repair options
   HA_CREATE_INFO create_info;
   LEX_MASTER_INFO mi;				// used by CHANGE MASTER
+  LEX_CONNECTION_OPTIONS conn_options;
   USER_RESOURCES mqh;
   ulong type;
   /*

--- 1.502/sql/sql_parse.cc	2005-12-28 08:47:55 -08:00
+++ 1.503/sql/sql_parse.cc	2006-01-30 15:06:59 -08:00
@@ -2341,6 +2341,7 @@
   SELECT_LEX_UNIT *unit= &lex->unit;
   /* Saved variable value */
   DBUG_ENTER("mysql_execute_command");
+
   thd->net.no_send_error= 0;
 
   /*
@@ -4836,6 +4837,17 @@
 #endif /* EMBEDDED_LIBRARY */
     break;
   }
+  case SQLCOM_CREATE_SERVER:
+  {
+    LEX *lex= thd->lex;
+    DBUG_PRINT("info", ("case SQLCOM_CREATE_SERVER"));
+    if (create_server(&lex->conn_options))
+    {
+      DBUG_PRINT("info", ("problem creating server")); 
+    }
+  }
+    send_ok(thd);
+    break;
   default:
     DBUG_ASSERT(0);                             /* Impossible */
     send_ok(thd);

--- 1.435/sql/sql_yacc.yy	2005-12-26 01:39:52 -08:00
+++ 1.436/sql/sql_yacc.yy	2006-01-30 15:07:00 -08:00
@@ -317,6 +317,7 @@
 %token  HELP_SYM
 %token  HEX_NUM
 %token  HIGH_PRIORITY
+%token  HOST_SYM
 %token  HOSTS_SYM
 %token  HOUR_MICROSECOND_SYM
 %token  HOUR_MINUTE_SYM
@@ -463,6 +464,7 @@
 %token  ONE_SYM
 %token  OPEN_SYM
 %token  OPTIMIZE
+%token  OPTIONS_SYM
 %token  OPTION
 %token  OPTIONALLY
 %token  OR2_SYM
@@ -472,6 +474,7 @@
 %token  OUTER
 %token  OUTFILE
 %token  OUT_SYM
+%token  OWNER_SYM
 %token  PACK_KEYS_SYM
 %token  PARSER_SYM
 %token  PARTIAL
@@ -485,6 +488,7 @@
 %token  POINT_SYM
 %token  POLYFROMTEXT
 %token  POLYGON
+%token  PORT_SYM
 %token  POSITION_SYM
 %token  PRECISION
 %token  PREPARE_SYM
@@ -553,6 +557,8 @@
 %token  SERIALIZABLE_SYM
 %token  SERIAL_SYM
 %token  SESSION_SYM
+%token  SERVER_SYM
+%token  SERVER_OPTIONS
 %token  SET
 %token  SET_VAR
 %token  SHARE_SYM
@@ -565,6 +571,7 @@
 %token  SLAVE
 %token  SMALLINT
 %token  SNAPSHOT_SYM
+%token  SOCKET_SYM
 %token  SONAME_SYM
 %token  SOUNDS_SYM
 %token  SPATIAL_SYM
@@ -667,6 +674,7 @@
 %token  WHILE_SYM
 %token  WITH
 %token  WORK_SYM
+%token  WRAPPER_SYM
 %token  WRITE_SYM
 %token  X509_SYM
 %token  XA_SYM
@@ -854,6 +862,7 @@
         view_algorithm view_or_trigger_tail view_suid view_tail view_list_opt
         view_list view_select view_check_option trigger_tail
         install uninstall partition_entry binlog_base64_event
+        server_def server_options_list server_option
 END_OF_INPUT
 
 %type <NONE> call sp_proc_stmts sp_proc_stmts1 sp_proc_stmt
@@ -1296,7 +1305,56 @@
 	  {
 	    Lex->sql_command = SQLCOM_CREATE_USER;
           }
+	| CREATE server_def
+	  {
+	    Lex->sql_command = SQLCOM_CREATE_SERVER;
+          }
 	;
+
+server_def:
+        SERVER_SYM ident_or_text WRAPPER_SYM ident_or_text OPTIONS_SYM '(' server_options_list ')'
+        {
+          Lex->conn_options.server_name= $2.str;
+          Lex->conn_options.scheme= $4.str;
+        }
+        ;
+
+server_options_list:
+        server_option
+        | server_options_list ',' server_option
+        ;
+
+server_option:
+        USER TEXT_STRING_sys
+        {
+          Lex->conn_options.username= $2.str;
+        }
+        |
+        HOST_SYM TEXT_STRING_sys
+        {
+          Lex->conn_options.username= $2.str;
+        }
+        |
+        OWNER_SYM TEXT_STRING_sys
+        {
+          Lex->conn_options.username= $2.str;
+        }
+        |
+        PASSWORD TEXT_STRING_sys
+        {
+          Lex->conn_options.password= $2.str;
+        }
+        |
+        SOCKET_SYM TEXT_STRING_sys
+        {
+          Lex->conn_options.socket= $2.str;
+        }
+        |
+        PORT_SYM ulong_num
+        {
+          Lex->conn_options.port= $2;
+        }
+        ;
 
 clear_privileges:
         /* Nothing */

--- 1.65/sql/share/errmsg.txt	2005-12-24 09:06:18 -08:00
+++ 1.66/sql/share/errmsg.txt	2006-01-30 15:06:59 -08:00
@@ -5733,3 +5733,6 @@
 	eng "Table definition on master and slave does not match"
 ER_BINLOG_ROW_RBR_TO_SBR
 	eng "Slave running with --log-slave-updates must use row-based binary logging to be able to replicate row-based binary log events"
+ER_FOREIGN_CONNECTION_DOESNT_EXIST
+        eng "The foreign connection name you are trying to reference does not exist. Data source error:  %-.64s"
+	ger "Die externe Verbindung, auf die Sie zugreifen wollen, existiert nicht. Datenquellenfehlermeldung:  %-.64s"

--- 1.76/libmysqld/Makefile.am	2005-12-22 20:04:23 -08:00
+++ 1.77/libmysqld/Makefile.am	2006-01-30 15:06:58 -08:00
@@ -65,7 +65,8 @@
 	sp_head.cc sp_pcontext.cc sp.cc sp_cache.cc sp_rcontext.cc \
 	parse_file.cc sql_view.cc sql_trigger.cc my_decimal.cc \
 	item_xmlfunc.cc \
-        rpl_filter.cc sql_partition.cc handlerton.cc sql_plugin.cc
+        rpl_filter.cc sql_partition.cc handlerton.cc sql_plugin.cc \
+	sql_connections.cc
 
 libmysqld_int_a_SOURCES= $(libmysqld_sources) $(libmysqlsources) $(sqlsources)
 EXTRA_libmysqld_a_SOURCES =	ha_innodb.cc ha_berkeley.cc ha_archive.cc \
--- New file ---
+++ libmysqld/sql_connections.cc	06/01/30 15:07:00
SYMLINK -> ../sql/sql_connections.cc

--- New file ---
+++ sql/sql_connections.cc	06/01/30 15:07:01
/* Copyright (C) 2000-2003 MySQL AB

   This program is free software; you can redistribute it and/or modify
   it under the terms of the GNU General Public License as published by
   the Free Software Foundation; either version 2 of the License, or
   (at your option) any later version.

   This program is distributed in the hope that it will be useful,
   but WITHOUT ANY WARRANTY; without even the implied warranty of
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   GNU General Public License for more details.

   You should have received a copy of the GNU General Public License
   along with this program; if not, write to the Free Software
   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA */


/*
  The connections are saved in the system table "connections"
*/

#include "mysql_priv.h"
#include "hash_filo.h"
#include <m_ctype.h>
#include <stdarg.h>
#include "sp_head.h"
#include "sp.h"

HASH connections_cache;
pthread_mutex_t connections_cache_mutex;                // To init the hash
uint connections_cache_initialised=FALSE;
/* Version of connection table. incremented by connections_load */
static uint connections_version=0;
static MEM_ROOT mem;
static bool initialized=0;
static my_bool connections_load(THD *thd, TABLE_LIST *tables);

static byte *connections_cache_get_key(SQL_CONNECTION *connection, uint *length,
			       my_bool not_used __attribute__((unused)))
{
  DBUG_ENTER("connections_cache_get_key");
  DBUG_PRINT("info", ("connection_name_length %d connection_name %s",
                      connection->connection_name_length,
                      connection->connection_name));

  *length= (uint) connection->connection_name_length;
  DBUG_RETURN((byte*) connection->connection_name);
}

/*
  Initialize structures responsible for connections used in federated
  connection scheme information for them from the connection
  table in the 'mysql' database.

  SYNOPSIS
    connections_init()
      dont_read_connection_table  TRUE if we want to skip loading data from
                            connection table and disable privilege checking.

  NOTES
    This function is mostly responsible for preparatory steps, main work
    on initialization and grants loading is done in connections_reload().

  RETURN VALUES
    0	ok
    1	Could not initialize connections
*/

my_bool connections_init(bool dont_read_connections_table)
{
  THD  *thd;
  my_bool return_val= 0;
  DBUG_ENTER("connections_init");

  if (pthread_mutex_init(&connections_cache_mutex, MY_MUTEX_INIT_FAST))
    DBUG_RETURN(1);

  if (hash_init(&connections_cache, system_charset_info, 32, 0, 0,
                (hash_get_key) connections_cache_get_key, 0, 0))
  {
    return_val= 1; /* we failed, out of memory? */
    goto end;
  }

  /* Initialize the mem root for data */
  init_alloc_root(&mem, ACL_ALLOC_BLOCK_SIZE, 0);

  connections_cache_initialised= TRUE;

  if (dont_read_connections_table)
  {
    DBUG_RETURN(0);
  }

  if (dont_read_connections_table)
    goto end;

  /*
    To be able to run this from boot, we allocate a temporary THD
  */
  if (!(thd=new THD))
    DBUG_RETURN(1); /* purecov: inspected */
  thd->thread_stack= (char*) &thd;
  thd->store_globals();
  /*
    It is safe to call connections_reload() since connections_* arrays and hashes which
    will be freed there are global static objects and thus are initialized
    by zeros at startup.
  */
  return_val= connections_reload(thd);
  delete thd;
  /* Remember that we don't have a THD */
  my_pthread_setspecific_ptr(THR_THD,  0);

end:
  DBUG_RETURN(return_val);
}

/*
  Initialize connection structures

  SYNOPSIS
    connections_load()
      thd     Current thread
      tables  List containing open "mysql.connections"

  RETURN VALUES
    FALSE  Success
    TRUE   Error
*/

static my_bool connections_load(THD *thd, TABLE_LIST *tables)
{
  TABLE *table;
  READ_RECORD read_record_info;
  my_bool return_val= 1;
  DBUG_ENTER("connections_load");

  if (!connections_cache_initialised)
    DBUG_RETURN(0);

  connections_version++; /* connections updated */


  /* first, send all cached rows to sleep with the fishes, oblivion!
     I expect this crappy comment replaced */
  free_root(&mem, MYF(MY_MARK_BLOCKS_FREE));
  my_hash_reset(&connections_cache);

  init_read_record(&read_record_info,thd,table=tables[0].table,NULL,1,0);
  while (!(read_record_info.read_record(&read_record_info)))
  {
    char *ptr;

    /* simple mistake, my_hash_insert expects a pointer, it does
       not copy the data anywhere. Now if you was using dynamic arrays
       it would be a different matter. So here, I allocate connection
       as a pointer. Obviously, remove this comment */

    SQL_CONNECTION *connection= (SQL_CONNECTION *)alloc_root(&mem,
                                                sizeof(SQL_CONNECTION));

    connection->connection_name= get_field(&mem, table->field[0]);
    connection->connection_name_length= strlen(connection->connection_name);
      //table->field[0]->field_length
      /// table->field[0]->charset()->mbmaxlen;
    connection->host= get_field(&mem, table->field[1]);
    connection->db= get_field(&mem, table->field[2]);
    connection->username= get_field(&mem, table->field[3]);
    connection->password= get_field(&mem, table->field[4]);
    connection->sport= get_field(&mem, table->field[5]);
    connection->port= connection->sport ? atoi(connection->sport) : 0;
    connection->socket= get_field(&mem, table->field[6]);
    connection->scheme= get_field(&mem, table->field[7]);
    connection->owner= get_field(&mem, table->field[8]);
    DBUG_PRINT("info", ("connection->connection_name %s", connection->connection_name));
    DBUG_PRINT("info", ("connection->host %s", connection->host));
    DBUG_PRINT("info", ("connection->db %s", connection->db));
    DBUG_PRINT("info", ("connection->username %s", connection->username));
    DBUG_PRINT("info", ("connection->password %s", connection->password));
    if (my_hash_insert(&connections_cache, (byte*) connection))
    {
      DBUG_PRINT("info", ("had a problem inserting connection %s at %lx",
                          connection->connection_name, connection));
      // error handling needed here
      return_val= 1;
      goto end;
    }
  }

  return_val=0;

end:
  end_read_record(&read_record_info);

  DBUG_RETURN(return_val);
}

my_bool create_server(LEX_CONNECTION_OPTIONS *conn_options)
{
  DBUG_ENTER("connection_create");
  DBUG_PRINT("info", ("conn_options->server_name %s", conn_options->server_name));
  DBUG_PRINT("info", ("conn_options->scheme %s", conn_options->scheme));

  DBUG_RETURN(FALSE);
}

void connections_free(bool end)
{
  DBUG_ENTER("connections_free");
  if (!connections_cache_initialised)
    DBUG_VOID_RETURN;
  VOID(pthread_mutex_destroy(&connections_cache_mutex));
  connections_cache_initialised=0;      /* maybe too permanant? 
                                           user will have to restart mysqld? */
  free_root(&mem,MYF(0));
  hash_free(&connections_cache);
  DBUG_VOID_RETURN;
}


/*
  Forget current connections cache and read new connections 
  from the conneciton table.

  SYNOPSIS
    connections_reload()
      thd  Current thread

  NOTE
    All tables of calling thread which were open and locked by LOCK TABLES
    statement will be unlocked and closed.
    This function is also used for initialization of structures responsible
    for user/db-level privilege checking.

  RETURN VALUE
    FALSE  Success
    TRUE   Failure
*/

my_bool connections_reload(THD *thd)
{
  TABLE_LIST tables[1];
  my_bool return_val= 1;
  DBUG_ENTER("connections_reload");

  if (thd->locked_tables)
  {					// Can't have locked tables here
    thd->lock=thd->locked_tables;
    thd->locked_tables=0;
    close_thread_tables(thd);
  }

  /*
    To avoid deadlocks we should obtain table locks before
    obtaining connections_cache->lock mutex.
  */
  bzero((char*) tables, sizeof(tables));
  tables[0].alias= tables[0].table_name= (char*) "connections";
  tables[0].db= (char*) "mysql";
  tables[0].lock_type= TL_READ;

  if (simple_open_n_lock_tables(thd, tables))
  {
    sql_print_error("Fatal error: Can't open and lock privilege tables: %s",
		    thd->net.last_error);
    goto end;
  }

  DBUG_PRINT("info", ("calling pthread_mutex_lock"));
  VOID(pthread_mutex_lock(&connections_cache_mutex));

  //old_connections_cache= connections_cache;
  //old_mem=mem;

  if ((return_val= connections_load(thd, tables)))
  {					// Error. Revert to old list
    /* blast, for now, we have no connections, discuss later way to preserve */

    DBUG_PRINT("error",("Reverting to old privileges"));
    connections_free();				/* purecov: inspected */
  }

  VOID(pthread_mutex_unlock(&connections_cache_mutex));

end:
  close_thread_tables(thd);
  DBUG_RETURN(return_val);
}


SQL_CONNECTION *get_connection_by_name(const char *connection_name)
{
  ulong error_num=0;
  uint i, connection_name_length;
  SQL_CONNECTION *connection;
  DBUG_ENTER("get_connection_by_connection_name");
  DBUG_PRINT("info", ("conneciton_name %s", connection_name));

  connection_name_length= strlen(connection_name);

  if (! connection_name || !strlen(connection_name))
  {
    DBUG_PRINT("info", ("connection_name not defined!"));
    error_num= 1;
    DBUG_RETURN((SQL_CONNECTION *)NULL);
  }

  if (!(connection= (SQL_CONNECTION *) hash_search(&connections_cache,
                                               (byte*) connection_name,
                                               connection_name_length)))
  {
    DBUG_PRINT("info", ("connection_name %s length %d not found!",
                        connection_name, connection_name_length));
    DBUG_RETURN((SQL_CONNECTION *)NULL);
  }
  DBUG_RETURN(connection);

}

--- New file ---
+++ sql/sql_connections.h	06/01/30 15:07:02
/* Copyright (C) 2000 MySQL AB & MySQL Finland AB & TCX DataKonsult AB

   This program is free software; you can redistribute it and/or modify
   it under the terms of the GNU General Public License as published by
   the Free Software Foundation; either version 2 of the License, or
   (at your option) any later version.

   This program is distributed in the hope that it will be useful,
   but WITHOUT ANY WARRANTY; without even the implied warranty of
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   GNU General Public License for more details.

   You should have received a copy of the GNU General Public License
   along with this program; if not, write to the Free Software
   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA */

#include "slave.h" // for tables_ok(), rpl_filter

/* structs */

typedef struct st_sql_connection
{
  char *connection_name;
  uint connection_name_length;
  uint table_name_length;
  uint port;
  char *db, *scheme, *username, *password, *socket, *sport, *table_name,
       *owner, *host;
} SQL_CONNECTION;

/* prototypes */
my_bool connections_init(bool dont_read_connection_table);
my_bool connections_reload(THD *thd);
my_bool create_server(LEX_CONNECTION_OPTIONS *conn_options);
void connections_free(bool end=0);
SQL_CONNECTION *get_connection_by_name(const char *connection_name);
bool connections_check_host(const char *host, const char *ip);


--- 1.46/sql/ha_federated.cc	2005-12-21 10:24:56 -08:00
+++ 1.47/sql/ha_federated.cc	2006-01-30 15:06:59 -08:00
@@ -579,13 +579,14 @@
   int buf_len;
   DBUG_ENTER("ha_federated parse_url_error");
 
-  if (share->scheme)
+  if (share->connection_string)
   {
     DBUG_PRINT("info",
                ("error: parse_url. Returning error code %d \
-                freeing share->scheme %lx", error_num, share->scheme));
-    my_free((gptr) share->scheme, MYF(0));
-    share->scheme= 0;
+                freeing share->connection_string %lx",
+                error_num, share->connection_string));
+    my_free((gptr) share->connection_string, MYF(0));
+    share->connection_string= 0;
   }
   buf_len= min(table->s->connect_string.length,
                FEDERATED_QUERY_BUFFER_SIZE-1);
@@ -595,6 +596,75 @@
 }
 
 /*
+  retrieve connection object which contains connection info 
+  from the system table given a connection name, set share
+  connection parameter members
+*/
+int get_connection(FEDERATED_SHARE *share)
+{
+  int error_num= ER_FOREIGN_CONNECTION_DOESNT_EXIST;
+  char error_buffer[FEDERATED_QUERY_BUFFER_SIZE];
+  SQL_CONNECTION *connection;
+  MYSQL *mysql_conn;
+  MYSQL_RES *result= 0;
+  MYSQL_ROW row;
+  DBUG_ENTER("ha_federated::get_connection");
+
+  if (!(connection=
+       get_connection_by_name(share->connection_string)))
+  {
+    DBUG_PRINT("info", ("get_connection_by_connection_name returned > 0 error condition!"));
+    /* need to come up with error handling */
+    error_num=1;
+    goto error;
+  }
+  DBUG_PRINT("info", ("get_connection_by_connection_name returned connection at %lx", connection));
+
+  /*
+    Most of these should never be empty strings, error handling will
+    need to be implemented. Also, is this the best way to set the share
+    members? Is there some allocation needed? In running this code, it works
+    except there are errors in the trace file of the share being overrun 
+    at the address of the share.
+  */
+  if (connection->connection_name)
+    share->connection_name= connection->connection_name;
+  share->connection_name_length= connection->connection_name_length ?
+    connection->connection_name_length : 0;
+  if (connection->username)
+    share->username= connection->username;
+  if (connection->password)
+    share->password= connection->password;
+  if (connection->db)
+    share->database= connection->db;
+  if (connection->sport)
+    share->sport= connection->sport;
+  share->port= connection->port ? connection->port : 0;
+  if (connection->host)
+    share->hostname= connection->host;
+  if (connection->socket)
+    share->socket= connection->socket;
+  if (connection->scheme)
+    share->scheme= connection->scheme;
+  else
+    share->scheme= NULL;
+
+  DBUG_PRINT("info", ("share->username %s", share->username));
+  DBUG_PRINT("info", ("share->password %s", share->password));
+  DBUG_PRINT("info", ("share->hostname %s", share->hostname));
+  DBUG_PRINT("info", ("share->database %s", share->database));
+  DBUG_PRINT("info", ("share->port %d", share->port));
+  DBUG_PRINT("info", ("share->socket %d", share->socket));
+  DBUG_RETURN(0);
+
+error:
+  my_sprintf(error_buffer,
+             (error_buffer, "connection name: '%s' doesn't exist!",
+              share->connection_string));
+  my_error(error_num, MYF(0), error_buffer);
+  DBUG_RETURN(error_num);
+}
+/*
   Parse connection info from table->s->connect_string
 
   SYNOPSIS
@@ -606,22 +676,39 @@
   DESCRIPTION
     Populates the share with information about the connection
     to the foreign database that will serve as the data source.
-    This string must be specified (currently) in the "comment" field,
+    This string must be specified (currently) in the "CONNECTION" field,
     listed in the CREATE TABLE statement.
 
     This string MUST be in the format of any of these:
 
-    scheme://username:password@hostname:port/database/table
-    scheme://username@hostname/database/table
-    scheme://username@hostname:port/database/table
-    scheme://username:password@hostname/database/table
+    CONNECTION="scheme://username:password@hostname:port/database/table"
+    CONNECTION="scheme://username@hostname/database/table"
+    CONNECTION="scheme://username@hostname:port/database/table"
+    CONNECTION="scheme://username:password@hostname/database/table"
+
+    _OR_
+
+    CONNECTION="connection name"
+
+    
 
   An Example:
 
-  mysql://joe:joespass@stripped:9308/federated/testtable
+  CREATE TABLE t1 (id int(32))
+    ENGINE="FEDERATED"
+    CONNECTION="mysql://joe:joespass@stripped:9308/federated/testtable";
+
+  CREATE TABLE t2 (
+    id int(4) NOT NULL auto_increment,
+    name varchar(32) NOT NULL,
+    PRIMARY KEY(id)
+    ) ENGINE="FEDERATED" CONNECTION="my_conn";
 
   ***IMPORTANT***
-  Currently, only "mysql://" is supported.
+  Currently, the Federated Storage Engine only supports connecting to another
+  MySQL Database ("scheme" of "mysql"). Connections using JDBC as well as 
+  other connectors are in the planning stage.
+  
 
   'password' and 'port' are both optional.
 
@@ -641,89 +728,121 @@
 
   share->port= 0;
   share->socket= 0;
+  DBUG_PRINT("info", ("share at %lx", share));
   DBUG_PRINT("info", ("Length: %d", table->s->connect_string.length));
-  DBUG_PRINT("info", ("String: '%.*s'", table->s->connect_string.length, 
+  DBUG_PRINT("info", ("String: '%.*s'", table->s->connect_string.length,
                       table->s->connect_string.str));
-  share->scheme= my_strdup_with_length((const byte*)table->s->
-                                       connect_string.str, 
+  share->connection_string= my_strdup_with_length((const byte*)table->s->
+                                       connect_string.str,
                                        table->s->connect_string.length,
                                        MYF(0));
 
   // Add a null for later termination of table name
-  share->scheme[table->s->connect_string.length]= 0;
-  DBUG_PRINT("info",("parse_url alloced share->scheme %lx", share->scheme));
-
-  /*
-    remove addition of null terminator and store length
-    for each string  in share
-  */
-  if (!(share->username= strstr(share->scheme, "://")))
-    goto error;
-  share->scheme[share->username - share->scheme]= '\0';
-
-  if (strcmp(share->scheme, "mysql") != 0)
-    goto error;
-
-  share->username+= 3;
+  share->connection_string[table->s->connect_string.length]= 0;
+  DBUG_PRINT("info",("parse_url alloced share->scheme %lx",
+                     share->connection_string));
+
+  /* No delimiters, must be a straight connection name */
+  if ( (!strchr(share->connection_string, '/')) &&
+       (!strchr(share->connection_string, '@')) &&
+       (!strchr(share->connection_string, ';')))
+  {
 
-  if (!(share->hostname= strchr(share->username, '@')))
-    goto error;
-    
-  share->username[share->hostname - share->username]= '\0';
-  share->hostname++;
+    DBUG_PRINT("info",
+               ("share->connection_string %s internal format \
+                share->connection_string",
+                share->connection_string, share->connection_string));
 
-  if ((share->password= strchr(share->username, ':')))
-  {
-    share->username[share->password - share->username]= '\0';
-    share->password++;
-    share->username= share->username;
-    /* make sure there isn't an extra / or @ */
-    if ((strchr(share->password, '/') || strchr(share->hostname, '@')))
+    if ((error_num= get_connection(share)))
       goto error;
+
     /*
-      Found that if the string is:
-      user:@hostname:port/database/table
-      Then password is a null string, so set to NULL
+      connection specifies everything but, resort to
+      expecting remote and foreign table names to match
     */
-    if ((share->password[0] == '\0'))
-      share->password= NULL;
+    share->table_name= table->s->table_name.str;
+    share->table_name_length= table->s->table_name.length;
+    share->table_name[share->table_name_length]= '\0';
   }
   else
-    share->username= share->username;
+  {
+    // Add a null for later termination of table name
+    share->connection_string[table->s->connect_string.length]= 0;
+    share->scheme= share->connection_string;
+    DBUG_PRINT("info",("parse_url alloced share->scheme %lx", share->scheme));
 
-  /* make sure there isn't an extra / or @ */
-  if ((strchr(share->username, '/')) || (strchr(share->hostname, '@')))
-    goto error;
+    /*
+      remove addition of null terminator and store length
+      for each string  in share
+    */
+    if (!(share->username= strstr(share->scheme, "://")))
+      goto error;
+    share->scheme[share->username - share->scheme]= '\0';
 
-  if (!(share->database= strchr(share->hostname, '/')))
-    goto error;
-  share->hostname[share->database - share->hostname]= '\0';
-  share->database++;
+    if (strcmp(share->scheme, "mysql") != 0)
+      goto error;
 
-  if ((share->sport= strchr(share->hostname, ':')))
-  {
-    share->hostname[share->sport - share->hostname]= '\0';
-    share->sport++;
-    if (share->sport[0] == '\0')
-      share->sport= NULL;
+    share->username+= 3;
+
+    if (!(share->hostname= strchr(share->username, '@')))
+      goto error;
+
+    share->username[share->hostname - share->username]= '\0';
+    share->hostname++;
+
+    if ((share->password= strchr(share->username, ':')))
+    {
+      share->username[share->password - share->username]= '\0';
+      share->password++;
+      share->username= share->username;
+      /* make sure there isn't an extra / or @ */
+      if ((strchr(share->password, '/') || strchr(share->hostname, '@')))
+        goto error;
+      /*
+        Found that if the string is:
+user:@hostname:port/db/table
+Then password is a null string, so set to NULL
+    */
+      if ((share->password[0] == '\0'))
+        share->password= NULL;
+    }
     else
-      share->port= atoi(share->sport);
-  }
+      share->username= share->username;
 
-  if (!(share->table_name= strchr(share->database, '/')))
-    goto error;
-  share->database[share->table_name - share->database]= '\0';
-  share->table_name++;
+    /* make sure there isn't an extra / or @ */
+    if ((strchr(share->username, '/')) || (strchr(share->hostname, '@')))
+      goto error;
 
-  share->table_name_length= strlen(share->table_name);
-      
-  /* make sure there's not an extra / */
-  if ((strchr(share->table_name, '/')))
-    goto error;
+    if (!(share->database= strchr(share->hostname, '/')))
+      goto error;
+    share->hostname[share->database - share->hostname]= '\0';
+    share->database++;
 
-  if (share->hostname[0] == '\0')
-    share->hostname= NULL;
+    if ((share->sport= strchr(share->hostname, ':')))
+    {
+      share->hostname[share->sport - share->hostname]= '\0';
+      share->sport++;
+      if (share->sport[0] == '\0')
+        share->sport= NULL;
+      else
+        share->port= atoi(share->sport);
+    }
+
+    if (!(share->table_name= strchr(share->database, '/')))
+      goto error;
+    share->database[share->table_name - share->database]= '\0';
+    share->table_name++;
 
+    share->table_name_length= strlen(share->table_name);
+
+    /* make sure there's not an extra / */
+    if ((strchr(share->table_name, '/')))
+      goto error;
+
+    if (share->hostname[0] == '\0')
+      share->hostname= NULL;
+
+  }
   if (!share->port)
   {
     if (strcmp(share->hostname, my_localhost) == 0)
@@ -734,7 +853,7 @@
 
   DBUG_PRINT("info",
              ("scheme: %s  username: %s  password: %s \
-               hostname: %s  port: %d  database: %s  tablename: %s",
+               hostname: %s  port: %d  db: %s  tablename: %s",
               share->scheme, share->username, share->password,
               share->hostname, share->port, share->database,
               share->table_name));
@@ -745,7 +864,6 @@
   DBUG_RETURN(parse_url_error(share, table, error_num));
 }
 
-
 /*****************************************************************************
 ** FEDERATED tables
 *****************************************************************************/
@@ -1403,8 +1521,13 @@
   if (!--share->use_count)
   {
     hash_delete(&federated_open_tables, (byte*) share);
-    my_free((gptr) share->scheme, MYF(MY_ALLOW_ZERO_PTR));
-    share->scheme= 0;
+    my_free((gptr) share->connection_string, MYF(MY_ALLOW_ZERO_PTR));
+    share->connection_string= 0;
+    if (share->socket)
+    {
+      my_free((gptr) share->socket, MYF(MY_ALLOW_ZERO_PTR));
+      share->socket= 0;
+    }
     thr_lock_delete(&share->lock);
     VOID(pthread_mutex_destroy(&share->mutex));
     my_free((gptr) share, MYF(0));
@@ -2597,7 +2720,7 @@
   if (!(retval= parse_url(&tmp_share, table_arg, 1)))
     retval= check_foreign_data_source(&tmp_share, 1);
 
-  my_free((gptr) tmp_share.scheme, MYF(MY_ALLOW_ZERO_PTR));
+  my_free((gptr) tmp_share.connection_string, MYF(MY_ALLOW_ZERO_PTR));
   DBUG_RETURN(retval);
 
 }

--- 1.25/sql/ha_federated.h	2005-11-23 12:47:26 -08:00
+++ 1.26/sql/ha_federated.h	2006-01-30 15:06:59 -08:00
@@ -129,6 +129,8 @@
   /*
     remote host info, parse_url supplies
   */
+  char *connection_name;
+  char *connection_string;
   char *scheme;
   char *hostname;
   char *username;
@@ -139,7 +141,7 @@
   char *socket;
   char *sport;
   ushort port;
-  uint table_name_length, use_count;
+  uint table_name_length, connection_name_length, use_count;
   pthread_mutex_t mutex;
   THR_LOCK lock;
 } FEDERATED_SHARE;
Thread
bk commit into 5.1 tree (patg:1.2047)Patrick Galbraith31 Jan