home *** CD-ROM | disk | FTP | other *** search
/ Chip 2001 January / Chip_2001-01_cd1.bin / tema / mysql / mysql-3.23.28g-win-source.exe / sql / sql_base.cpp < prev    next >
C/C++ Source or Header  |  2000-11-21  |  54KB  |  2,037 lines

  1. /* Copyright (C) 2000 MySQL AB & MySQL Finland AB & TCX DataKonsult AB
  2.  
  3.    This program is free software; you can redistribute it and/or modify
  4.    it under the terms of the GNU General Public License as published by
  5.    the Free Software Foundation; either version 2 of the License, or
  6.    (at your option) any later version.
  7.  
  8.    This program is distributed in the hope that it will be useful,
  9.    but WITHOUT ANY WARRANTY; without even the implied warranty of
  10.    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  11.    GNU General Public License for more details.
  12.  
  13.    You should have received a copy of the GNU General Public License
  14.    along with this program; if not, write to the Free Software
  15.    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA */
  16.  
  17.  
  18. /* Basic functions neaded by many modules */
  19.  
  20. #include "mysql_priv.h"
  21. #include "sql_acl.h"
  22. #include <thr_alarm.h>
  23. #include <m_ctype.h>
  24. #include <my_dir.h>
  25. #include <hash.h>
  26. #include <nisam.h>
  27. #include <assert.h>
  28. #ifdef    __WIN__
  29. #include <io.h>
  30. #endif
  31.  
  32. TABLE *unused_tables;                /* Used by mysql_test */
  33. HASH open_cache;                /* Used by mysql_test */
  34.  
  35.  
  36. static int open_unireg_entry(THD *thd,TABLE *entry,const char *db,
  37.                  const char *name, const char *alias, bool locked);
  38. static bool insert_fields(THD *thd,TABLE_LIST *tables, const char *table_name,
  39.               List_iterator<Item> *it);
  40. static void free_cache_entry(TABLE *entry);
  41. static void mysql_rm_tmp_tables(void);
  42. static key_map get_key_map_from_key_list(THD *thd, TABLE *table,
  43.                      List<String> *index_list);
  44.  
  45.  
  46. static byte *cache_key(const byte *record,uint *length,
  47.                my_bool not_used __attribute__((unused)))
  48. {
  49.   TABLE *entry=(TABLE*) record;
  50.   *length=entry->key_length;
  51.   return (byte*) entry->table_cache_key;
  52. }
  53.  
  54. void table_cache_init(void)
  55. {
  56.   VOID(hash_init(&open_cache,table_cache_size+16,0,0,cache_key,
  57.          (void (*)(void*)) free_cache_entry,0));
  58.   mysql_rm_tmp_tables();
  59. }
  60.  
  61.  
  62. void table_cache_free(void)
  63. {
  64.   DBUG_ENTER("table_cache_free");
  65.   close_cached_tables((THD*) 0,0,(TABLE_LIST*) 0);
  66.   if (!open_cache.records)            // Safety first
  67.     hash_free(&open_cache);
  68.   DBUG_VOID_RETURN;
  69. }
  70.  
  71.  
  72. uint cached_tables(void)
  73. {
  74.   return open_cache.records;
  75. }
  76.  
  77. #ifdef EXTRA_DEBUG
  78. static void check_unused(void)
  79. {
  80.   uint count=0,idx=0;
  81.   TABLE *cur_link,*start_link;
  82.  
  83.   if ((start_link=cur_link=unused_tables))
  84.   {
  85.     do
  86.     {
  87.       if (cur_link != cur_link->next->prev || cur_link != cur_link->prev->next)
  88.       {
  89.     DBUG_PRINT("error",("Unused_links aren't linked properly")); /* purecov: inspected */
  90.     return; /* purecov: inspected */
  91.       }
  92.     } while (count++ < open_cache.records &&
  93.          (cur_link=cur_link->next) != start_link);
  94.     if (cur_link != start_link)
  95.     {
  96.       DBUG_PRINT("error",("Unused_links aren't connected")); /* purecov: inspected */
  97.     }
  98.   }
  99.   for (idx=0 ; idx < open_cache.records ; idx++)
  100.   {
  101.     TABLE *entry=(TABLE*) hash_element(&open_cache,idx);
  102.     if (!entry->in_use)
  103.       count--;
  104.   }
  105.   if (count != 0)
  106.   {
  107.     DBUG_PRINT("error",("Unused_links doesn't match open_cache: diff: %d", /* purecov: inspected */
  108.             count)); /* purecov: inspected */
  109.   }
  110. }
  111. #else
  112. #define check_unused()
  113. #endif
  114.  
  115.  
  116.  
  117. /******************************************************************************
  118. ** Send name and type of result to client.
  119. ** Sum fields has table name empty and field_name.
  120. ******************************************************************************/
  121.  
  122. bool
  123. send_fields(THD *thd,List<Item> &list,uint flag)
  124. {
  125.   List_iterator<Item> it(list);
  126.   Item *item;
  127.   char buff[80];
  128.   CONVERT *convert=thd->convert_set;
  129.  
  130.   String tmp((char*) buff,sizeof(buff)),*res,*packet= &thd->packet;
  131.  
  132.   if (thd->fatal_error)        // We have got an error
  133.     goto err;
  134.  
  135.   if (flag & 1)
  136.   {                // Packet with number of elements
  137.     char *pos=net_store_length(buff,(uint) list.elements);
  138.     (void) my_net_write(&thd->net, buff,(uint) (pos-buff));
  139.   }
  140.   while ((item=it++))
  141.   {
  142.     char *pos;
  143.     Send_field field;
  144.     item->make_field(&field);
  145.     packet->length(0);
  146.  
  147.     if (convert)
  148.     {
  149.       if (convert->store(packet,field.table_name,
  150.              (uint) strlen(field.table_name)) ||
  151.       convert->store(packet,field.col_name,
  152.              (uint) strlen(field.col_name)) ||
  153.       packet->realloc(packet->length()+10))
  154.     goto err;
  155.     }
  156.     else if (net_store_data(packet,field.table_name) ||
  157.          net_store_data(packet,field.col_name) ||
  158.          packet->realloc(packet->length()+10))
  159.       goto err; /* purecov: inspected */
  160.     pos= (char*) packet->ptr()+packet->length();
  161.  
  162.     if (!(thd->client_capabilities & CLIENT_LONG_FLAG))
  163.     {
  164.       packet->length(packet->length()+9);
  165.       pos[0]=3; int3store(pos+1,field.length);
  166.       pos[4]=1; pos[5]=field.type;
  167.       pos[6]=2; pos[7]=(char) field.flags; pos[8]= (char) field.decimals;
  168.     }
  169.     else
  170.     {
  171.       packet->length(packet->length()+10);
  172.       pos[0]=3; int3store(pos+1,field.length);
  173.       pos[4]=1; pos[5]=field.type;
  174.       pos[6]=3; int2store(pos+7,field.flags); pos[9]= (char) field.decimals;
  175.     }
  176.     if (flag & 2)
  177.     {                        // Send default value
  178.       if (!(res=item->val_str(&tmp)))
  179.       {
  180.     if (net_store_null(packet))
  181.       goto err;
  182.       }
  183.       else if (net_store_data(packet,res->ptr(),res->length()))
  184.     goto err;
  185.     }
  186.     if (my_net_write(&thd->net, (char*) packet->ptr(),packet->length()))
  187.       break;                    /* purecov: inspected */
  188.   }
  189.   send_eof(&thd->net,(test_flags & TEST_MIT_THREAD) ? 0: 1);
  190.   return 0;
  191.  err:
  192.   send_error(&thd->net,ER_OUT_OF_RESOURCES);    /* purecov: inspected */
  193.   return 1;                    /* purecov: inspected */
  194. }
  195.  
  196.  
  197. /*****************************************************************************
  198.  *     Functions to free open table cache
  199.  ****************************************************************************/
  200.  
  201.  
  202. void intern_close_table(TABLE *table)
  203. {                        // Free all structures
  204.   free_io_cache(table);
  205.   if (table->file)
  206.     VOID(closefrm(table));            // close file
  207. }
  208.  
  209.  
  210. static void free_cache_entry(TABLE *table)
  211. {
  212.   DBUG_ENTER("free_cache_entry");
  213.  
  214.   intern_close_table(table);
  215.   if (!table->in_use)
  216.   {
  217.     table->next->prev=table->prev;        /* remove from used chain */
  218.     table->prev->next=table->next;
  219.     if (table == unused_tables)
  220.     {
  221.       unused_tables=unused_tables->next;
  222.       if (table == unused_tables)
  223.     unused_tables=0;
  224.     }
  225.     check_unused();                // consisty check
  226.   }
  227.   my_free((gptr) table,MYF(0));
  228.   DBUG_VOID_RETURN;
  229. }
  230.  
  231.  
  232. void free_io_cache(TABLE *table)
  233. {
  234.   if (table->io_cache)
  235.   {
  236.     close_cached_file(table->io_cache);
  237.     my_free((gptr) table->io_cache,MYF(0));
  238.     table->io_cache=0;
  239.   }
  240.   if (table->record_pointers)
  241.   {
  242.     my_free((gptr) table->record_pointers,MYF(0));
  243.     table->record_pointers=0;
  244.   }
  245. }
  246.  
  247.     /* Close all tables which aren't in use by any thread */
  248.  
  249. bool close_cached_tables(THD *thd, bool if_wait_for_refresh,
  250.              TABLE_LIST *tables)
  251. {
  252.   bool result=0;
  253.   DBUG_ENTER("close_cached_tables");
  254.  
  255.   VOID(pthread_mutex_lock(&LOCK_open));
  256.   if (!tables)
  257.   {
  258.     while (unused_tables)
  259.     {
  260. #ifdef EXTRA_DEBUG
  261.       if (hash_delete(&open_cache,(byte*) unused_tables))
  262.     printf("Warning: Couldn't delete open table from hash\n");
  263. #else
  264.       VOID(hash_delete(&open_cache,(byte*) unused_tables));
  265. #endif
  266.     }
  267.     if (!open_cache.records && ! locked_in_memory)
  268.     {
  269.       end_key_cache();                /* No tables in memory */
  270.     }
  271.     refresh_version++;                // Force close of open tables
  272.   }
  273.   else
  274.   {
  275.     bool found=0;
  276.     for (TABLE_LIST *table=tables ; table ; table=table->next)
  277.     {
  278.       if (remove_table_from_cache(thd, table->db, table->name))
  279.     found=1;
  280.     }
  281.     if (!found)
  282.       if_wait_for_refresh=0;            // Nothing to wait for
  283.   }
  284.   if (if_wait_for_refresh)
  285.   {
  286.     /*
  287.       If there is any table that has a lower refresh_version, wait until
  288.       this is closed (or this thread is killed) before returning
  289.     */
  290.     if (!tables)
  291.       kill_delayed_threads();
  292.     pthread_mutex_lock(&thd->mysys_var->mutex);
  293.     thd->mysys_var->current_mutex= &LOCK_open;
  294.     thd->mysys_var->current_cond= &COND_refresh;
  295.     thd->proc_info="Flushing tables";
  296.     pthread_mutex_unlock(&thd->mysys_var->mutex);
  297.  
  298.     close_old_data_files(thd,thd->open_tables,1,1);
  299.     bool found=1;
  300.     /* Wait until all threads has closed all the tables we had locked */
  301.     DBUG_PRINT("info", ("Waiting for others threads to close their open tables"));
  302.     while (found && ! thd->killed)
  303.     {
  304.       found=0;
  305.       for (uint idx=0 ; idx < open_cache.records ; idx++)
  306.       {
  307.     TABLE *table=(TABLE*) hash_element(&open_cache,idx);
  308.     if ((table->version) < refresh_version && table->db_stat)
  309.     {
  310.       found=1;
  311.       pthread_cond_wait(&COND_refresh,&LOCK_open);
  312.       break;
  313.     }
  314.       }
  315.     }
  316.     /*
  317.       No other thread has the locked tables open; reopen them and get the
  318.       old locks. This should always succeed (unless some external process
  319.       has removed the tables)
  320.     */
  321.     thd->in_lock_tables=1;
  322.     result=reopen_tables(thd,1,1);
  323.     thd->in_lock_tables=0;
  324.   }
  325.   VOID(pthread_mutex_unlock(&LOCK_open));
  326.   if (if_wait_for_refresh)
  327.   {
  328.     THD *thd=current_thd;
  329.     pthread_mutex_lock(&thd->mysys_var->mutex);
  330.     thd->mysys_var->current_mutex= 0;
  331.     thd->mysys_var->current_cond= 0;
  332.     thd->proc_info=0;
  333.     pthread_mutex_unlock(&thd->mysys_var->mutex);
  334.   }
  335.   DBUG_RETURN(result);
  336. }
  337.  
  338.  
  339. /* Put all tables used by thread in free list */
  340.  
  341. void close_thread_tables(THD *thd, bool locked)
  342. {
  343.   DBUG_ENTER("close_thread_tables");
  344.  
  345.   if (thd->locked_tables)
  346.     DBUG_VOID_RETURN;                // LOCK TABLES in use
  347.  
  348.   TABLE *table,*next;
  349.   bool found_old_table=0;
  350.  
  351.   if (thd->lock)
  352.   {
  353.     mysql_unlock_tables(thd, thd->lock); thd->lock=0;
  354.   }
  355.   /* VOID(pthread_sigmask(SIG_SETMASK,&thd->block_signals,NULL)); */
  356.   if (!locked)
  357.     VOID(pthread_mutex_lock(&LOCK_open));
  358.  
  359.   DBUG_PRINT("info", ("thd->open_tables=%p", thd->open_tables));
  360.  
  361.   for (table=thd->open_tables ; table ; table=next)
  362.   {
  363.     next=table->next;
  364.     if (table->version != refresh_version ||
  365.     thd->version != refresh_version || !table->db_stat)
  366.     {
  367.       VOID(hash_delete(&open_cache,(byte*) table));
  368.       found_old_table=1;
  369.     }
  370.     else
  371.     {
  372.       if (table->flush_version != flush_version)
  373.       {
  374.     table->flush_version=flush_version;
  375.     table->file->extra(HA_EXTRA_FLUSH);
  376.       }
  377.       table->in_use=0;
  378.       if (unused_tables)
  379.       {
  380.     table->next=unused_tables;        /* Link in last */
  381.     table->prev=unused_tables->prev;
  382.     unused_tables->prev=table;
  383.     table->prev->next=table;
  384.       }
  385.       else
  386.     unused_tables=table->next=table->prev=table;
  387.     }
  388.   }
  389.   thd->open_tables=0;
  390.   /* Free tables to hold down open files */
  391.   while (open_cache.records > table_cache_size && unused_tables)
  392.     VOID(hash_delete(&open_cache,(byte*) unused_tables)); /* purecov: tested */
  393.   check_unused();
  394.   if (found_old_table)
  395.   {
  396.     /* Tell threads waiting for refresh that something has happened */
  397.     VOID(pthread_cond_broadcast(&COND_refresh));
  398.   }
  399.   if (!locked)
  400.     VOID(pthread_mutex_unlock(&LOCK_open));
  401.   /*  VOID(pthread_sigmask(SIG_SETMASK,&thd->signals,NULL)); */
  402.   DBUG_VOID_RETURN;
  403. }
  404.  
  405.     /* Close and delete temporary tables */
  406.  
  407. void close_temporary(TABLE *table,bool delete_table)
  408. {
  409.   DBUG_ENTER("close_temporary");
  410.   char path[FN_REFLEN];
  411.   db_type table_type=table->db_type;
  412.   strmov(path,table->path);
  413.   free_io_cache(table);
  414.   closefrm(table);
  415.   my_free((char*) table,MYF(0));
  416.   if (delete_table)
  417.     rm_temporary_table(table_type, path);
  418.   DBUG_VOID_RETURN;
  419. }
  420.  
  421.  
  422. void close_temporary_tables(THD *thd)
  423. {
  424.   TABLE *table,*next;
  425.   for (table=thd->temporary_tables ; table ; table=next)
  426.   {
  427.     next=table->next;
  428.     close_temporary(table);
  429.   }
  430.   thd->temporary_tables=0;
  431. }
  432.  
  433.  
  434. TABLE **find_temporary_table(THD *thd, const char *db, const char *table_name)
  435. {
  436.   char    key[MAX_DBKEY_LENGTH];
  437.   uint    key_length= (uint) (strmov(strmov(key,db)+1,table_name)-key)+1;
  438.   TABLE *table,**prev;
  439.  
  440.   prev= &thd->temporary_tables;
  441.   for (table=thd->temporary_tables ; table ; table=table->next)
  442.   {
  443.     if (table->key_length == key_length &&
  444.     !memcmp(table->table_cache_key,key,key_length))
  445.       return prev;
  446.     prev= &table->next;
  447.   }
  448.   return 0;                    // Not a temporary table
  449. }
  450.  
  451. bool close_temporary_table(THD *thd, const char *db, const char *table_name)
  452. {
  453.   TABLE *table,**prev;
  454.  
  455.   if (!(prev=find_temporary_table(thd,db,table_name)))
  456.     return 1;
  457.   table= *prev;
  458.   *prev= table->next;
  459.   close_temporary(table);
  460.   return 0;
  461. }
  462.  
  463. bool rename_temporary_table(TABLE *table, const char *db,
  464.                 const char *table_name)
  465. {
  466.   char *key;
  467.   if (!(key=(char*) alloc_root(&table->mem_root,
  468.                    (uint) strlen(db)+
  469.                    (uint) strlen(table_name)+2)))
  470.     return 1;                /* purecov: inspected */
  471.   table->key_length=(uint)
  472.     (strmov((table->real_name=strmov(table->table_cache_key=key,
  473.                      db)+1),
  474.         table_name) - table->table_cache_key)+1;
  475.   return 0;
  476. }
  477.  
  478.  
  479.  
  480.  
  481.     /* move table first in unused links */
  482.  
  483. static void relink_unused(TABLE *table)
  484. {
  485.   if (table != unused_tables)
  486.   {
  487.     table->prev->next=table->next;        /* Remove from unused list */
  488.     table->next->prev=table->prev;
  489.     table->next=unused_tables;            /* Link in unused tables */
  490.     table->prev=unused_tables->prev;
  491.     unused_tables->prev->next=table;
  492.     unused_tables->prev=table;
  493.     unused_tables=table;
  494.     check_unused();
  495.   }
  496. }
  497.  
  498.  
  499. /*
  500.   Remove all instances of table from the current open list
  501.   Free all locks on tables that are done with LOCK TABLES
  502.  */
  503.  
  504. TABLE *unlink_open_table(THD *thd, TABLE *list, TABLE *find)
  505. {
  506.   char key[MAX_DBKEY_LENGTH];
  507.   uint key_length=find->key_length;
  508.   TABLE *start=list,**prev,*next;
  509.   prev= &start;
  510.   memcpy(key,find->table_cache_key,key_length);
  511.   for (; list ; list=next)
  512.   {
  513.     next=list->next;
  514.     if (list->key_length == key_length &&
  515.     !memcmp(list->table_cache_key,key,key_length))
  516.     {
  517.       if (thd->locked_tables)
  518.     mysql_lock_remove(thd, thd->locked_tables,list);
  519.       VOID(hash_delete(&open_cache,(byte*) list)); // Close table
  520.     }
  521.     else
  522.     {
  523.       *prev=list;                // put in use list
  524.       prev= &list->next;
  525.     }
  526.   }
  527.   *prev=0;
  528.   // Notify any 'refresh' threads
  529.   pthread_cond_broadcast(&COND_refresh);
  530.   return start;
  531. }
  532.  
  533.  
  534. /*
  535.    When we call the following function we must have a lock on
  536.    LOCK_OPEN ; This lock will be unlocked on return.
  537. */
  538.  
  539. void wait_for_refresh(THD *thd)
  540. {
  541.   /* Wait until the current table is up to date */
  542.   const char *proc_info;
  543.   pthread_mutex_lock(&thd->mysys_var->mutex);
  544.   thd->mysys_var->current_mutex= &LOCK_open;
  545.   thd->mysys_var->current_cond= &COND_refresh;
  546.   proc_info=thd->proc_info;
  547.   thd->proc_info="Waiting for table";
  548.   pthread_mutex_unlock(&thd->mysys_var->mutex);
  549.   (void) pthread_cond_wait(&COND_refresh,&LOCK_open);
  550.  
  551.   pthread_mutex_unlock(&LOCK_open);    // Must be unlocked first
  552.   pthread_mutex_lock(&thd->mysys_var->mutex);
  553.   thd->mysys_var->current_mutex= 0;
  554.   thd->mysys_var->current_cond= 0;
  555.   thd->proc_info= proc_info;
  556.   pthread_mutex_unlock(&thd->mysys_var->mutex);
  557. }
  558.  
  559. TABLE *reopen_name_locked_table(THD* thd, TABLE_LIST* table_list)
  560. {
  561.   DBUG_ENTER("reopen_name_locked_table");
  562.   if (thd->killed)
  563.     DBUG_RETURN(0);
  564.   TABLE* table;
  565.   if(!(table = table_list->table))
  566.     DBUG_RETURN(0);
  567.  
  568.   char* db = thd->db ? thd->db : table_list->db;
  569.   char* table_name = table_list->name;
  570.   char    key[MAX_DBKEY_LENGTH];
  571.   uint    key_length;
  572.   key_length=(uint) (strmov(strmov(key,db)+1,table_name)-key)+1;
  573.  
  574.   pthread_mutex_lock(&LOCK_open);
  575.   if (open_unireg_entry(thd, table, db, table_name, table_name,0) ||
  576.       !(table->table_cache_key =memdup_root(&table->mem_root,(char*) key,
  577.                         key_length)))
  578.     {
  579.       closefrm(table);
  580.       pthread_mutex_unlock(&LOCK_open);
  581.       DBUG_RETURN(0);
  582.     }
  583.   
  584.   table->key_length=key_length;
  585.   table->version=0;
  586.   table->flush_version=0;
  587.   if (!key_cache_inited)
  588.     ha_key_cache();
  589.   table->in_use = thd;
  590.   check_unused();
  591.   pthread_mutex_unlock(&LOCK_open);
  592.   table->next = thd->open_tables;
  593.   thd->open_tables = table;
  594.   table->tablenr=thd->current_tablenr++;
  595.   table->used_fields=0;
  596.   table->const_table=0;
  597.   table->outer_join=table->null_row=table->maybe_null=0;
  598.   table->status=STATUS_NO_RECORD;
  599.   table->keys_in_use_for_query=table->used_keys= table->keys_in_use;
  600.   DBUG_RETURN(table);  
  601. }
  602.  
  603.  
  604. /******************************************************************************
  605. ** open a table
  606. ** Uses a cache of open tables to find a table not in use.
  607. ** If refresh is a NULL pointer, then the is no version number checking and
  608. ** the table is not put in the thread-open-list
  609. ** If the return value is NULL and refresh is set then one must close
  610. ** all tables and retry the open
  611. ******************************************************************************/
  612.  
  613.  
  614. TABLE *open_table(THD *thd,const char *db,const char *table_name,
  615.           const char *alias,bool *refresh)
  616. {
  617.   reg1    TABLE *table;
  618.   char    key[MAX_DBKEY_LENGTH];
  619.   uint    key_length;
  620.   DBUG_ENTER("open_table");
  621.  
  622.   /* find a unused table in the open table cache */
  623.   if (refresh)
  624.     *refresh=0;
  625.   if (thd->killed)
  626.     DBUG_RETURN(0);
  627.   key_length=(uint) (strmov(strmov(key,db)+1,table_name)-key)+1;
  628.  
  629.   for (table=thd->temporary_tables; table ; table=table->next)
  630.   {
  631.     if (table->key_length == key_length &&
  632.     !memcmp(table->table_cache_key,key,key_length))
  633.     {
  634.       if (table->query_id == thd->query_id)
  635.       {
  636.     my_printf_error(ER_CANT_REOPEN_TABLE,
  637.             ER(ER_CANT_REOPEN_TABLE),MYF(0),table->table_name);
  638.     DBUG_RETURN(0);
  639.       }
  640.       table->query_id=thd->query_id;
  641.       goto reset;
  642.     }
  643.   }
  644.  
  645.   if (thd->locked_tables)
  646.   {                        // Using table locks
  647.     for (table=thd->open_tables; table ; table=table->next)
  648.     {
  649.       if (table->key_length == key_length &&
  650.       !memcmp(table->table_cache_key,key,key_length) &&
  651.       !my_strcasecmp(table->table_name,alias))
  652.     goto reset;
  653.     }
  654.     my_printf_error(ER_TABLE_NOT_LOCKED,ER(ER_TABLE_NOT_LOCKED),MYF(0),alias);
  655.     DBUG_RETURN(0);
  656.   }
  657.   VOID(pthread_mutex_lock(&LOCK_open));
  658.  
  659.   if (!thd->open_tables)
  660.     thd->version=refresh_version;
  661.   else if (thd->version != refresh_version && refresh)
  662.   {
  663.     /* Someone did a refresh while thread was opening tables */
  664.     *refresh=1;
  665.     VOID(pthread_mutex_unlock(&LOCK_open));
  666.     DBUG_RETURN(0);
  667.   }
  668.  
  669.   for (table=(TABLE*) hash_search(&open_cache,(byte*) key,key_length) ;
  670.        table && table->in_use ;
  671.        table = (TABLE*) hash_next(&open_cache,(byte*) key,key_length))
  672.   {
  673.     if (table->version != refresh_version)
  674.     {
  675.       /*
  676.       ** There is a refresh in progress for this table
  677.       ** Wait until the table is freed or the thread is killed.
  678.       */
  679.       close_old_data_files(thd,thd->open_tables,0,0);
  680.       if (table->in_use != thd)
  681.     wait_for_refresh(thd);
  682.       else
  683.     VOID(pthread_mutex_unlock(&LOCK_open));
  684.       if (refresh)
  685.     *refresh=1;
  686.       DBUG_RETURN(0);
  687.     }
  688.   }
  689.   if (table)
  690.   {
  691.     if (table == unused_tables)
  692.     {                        // First unused
  693.       unused_tables=unused_tables->next;    // Remove from link
  694.       if (table == unused_tables)
  695.     unused_tables=0;
  696.     }
  697.     table->prev->next=table->next;        /* Remove from unused list */
  698.     table->next->prev=table->prev;
  699.   }
  700.   else
  701.   {
  702.     /* Free cache if too big */
  703.     while (open_cache.records > table_cache_size && unused_tables)
  704.       VOID(hash_delete(&open_cache,(byte*) unused_tables)); /* purecov: tested */
  705.  
  706.     /* make a new table */
  707.     if (!(table=(TABLE*) my_malloc(sizeof(*table),MYF(MY_WME))))
  708.       DBUG_RETURN(NULL);
  709.     if (open_unireg_entry(thd, table,db,table_name,alias,1) ||
  710.     !(table->table_cache_key=memdup_root(&table->mem_root,(char*) key,
  711.                          key_length)))
  712.     {
  713.       MEM_ROOT* glob_alloc;
  714.       LINT_INIT(glob_alloc);
  715.  
  716.       if (errno == ENOENT &&
  717.      (glob_alloc = my_pthread_getspecific_ptr(MEM_ROOT*,THR_MALLOC)))
  718.     // Sasha: needed for replication
  719.     // remember the name of the non-existent table
  720.     // so we can try to download it from the master
  721.       {
  722.     int table_name_len = (uint) strlen(table_name);
  723.     int db_len = (uint) strlen(db);
  724.     thd->last_nx_db = alloc_root(glob_alloc,db_len + table_name_len + 2);
  725.     if(thd->last_nx_db)
  726.     {
  727.       thd->last_nx_table = thd->last_nx_db + db_len + 1;
  728.       memcpy(thd->last_nx_table, table_name, table_name_len + 1);
  729.       memcpy(thd->last_nx_db, db, db_len + 1);
  730.     }
  731.       }
  732.       table->next=table->prev=table;
  733.       free_cache_entry(table);
  734.       VOID(pthread_mutex_unlock(&LOCK_open));
  735.       DBUG_RETURN(NULL);
  736.     }
  737.     table->key_length=key_length;
  738.     table->version=refresh_version;
  739.     table->flush_version=flush_version;
  740.     if (!key_cache_inited)
  741.       ha_key_cache();
  742.     DBUG_PRINT("info", ("inserting table %p into the cache", table));
  743.     VOID(hash_insert(&open_cache,(byte*) table));
  744.   }
  745.  
  746.   table->in_use=thd;
  747.   check_unused();
  748.   VOID(pthread_mutex_unlock(&LOCK_open));
  749.   if (refresh)
  750.   {
  751.     table->next=thd->open_tables;        /* Link into simple list */
  752.     thd->open_tables=table;
  753.   }
  754.   table->reginfo.lock_type=TL_READ;        /* Assume read */
  755.  
  756.  reset:
  757.   /* Fix alias if table name changes */
  758.   if (strcmp(table->table_name,alias))
  759.   {
  760.     uint length=(uint) strlen(alias)+1;
  761.     table->table_name= (char*) my_realloc(table->table_name,length,
  762.                       MYF(MY_WME));
  763.     memcpy(table->table_name,alias,length);
  764.     for (uint i=0 ; i < table->fields ; i++)
  765.       table->field[i]->table_name=table->table_name;
  766.   }
  767.   /* These variables are also set in reopen_table() */
  768.   table->tablenr=thd->current_tablenr++;
  769.   table->used_fields=0;
  770.   table->const_table=0;
  771.   table->outer_join=table->null_row=table->maybe_null=0;
  772.   table->status=STATUS_NO_RECORD;
  773.   table->keys_in_use_for_query=table->used_keys= table->keys_in_use;
  774.   dbug_assert(table->key_read == 0);
  775.   DBUG_RETURN(table);
  776. }
  777.  
  778.  
  779. TABLE *find_locked_table(THD *thd, const char *db,const char *table_name)
  780. {
  781.   char    key[MAX_DBKEY_LENGTH];
  782.   uint key_length=(uint) (strmov(strmov(key,db)+1,table_name)-key)+1;
  783.  
  784.   for (TABLE *table=thd->open_tables; table ; table=table->next)
  785.   {
  786.     if (table->key_length == key_length &&
  787.     !memcmp(table->table_cache_key,key,key_length))
  788.       return table;
  789.   }
  790.   return(0);
  791. }
  792.  
  793.  
  794. /****************************************************************************
  795. ** Reopen an table because the definition has changed. The date file for the
  796. ** table is already closed.
  797. ** Returns 0 if ok.
  798. ** If table can't be reopened, the entry is unchanged.
  799. ****************************************************************************/
  800.  
  801. bool reopen_table(TABLE *table,bool locked)
  802. {
  803.   TABLE tmp;
  804.   char *db=table->table_cache_key;
  805.   char *table_name=table->real_name;
  806.   bool error=1;
  807.   Field **field;
  808.   uint key,part;
  809.   DBUG_ENTER("reopen_table");
  810.  
  811. #ifdef EXTRA_DEBUG
  812.   if (table->db_stat)
  813.     sql_print_error("Table %s had a open data handler in reopen_table",
  814.             table->table_name);
  815. #endif
  816.   if (!locked)
  817.     VOID(pthread_mutex_lock(&LOCK_open));
  818.  
  819.   if (open_unireg_entry(current_thd,&tmp,db,table_name,table->table_name,
  820.             locked))
  821.     goto end;
  822.   free_io_cache(table);
  823.  
  824.   if (!(tmp.table_cache_key= memdup_root(&tmp.mem_root,db,
  825.                      table->key_length)))
  826.   {
  827.     closefrm(&tmp);                // End of memory
  828.     goto end;
  829.   }
  830.  
  831.   tmp.key_length=table->key_length;
  832.   tmp.in_use=table->in_use;
  833.   tmp.used_keys=tmp.keys_in_use;
  834.   tmp.reginfo.lock_type=table->reginfo.lock_type;
  835.   tmp.version=refresh_version;
  836.   tmp.next=table->next;
  837.   tmp.prev=table->prev;
  838.  
  839.   /* This list copies varibles set by open_table */
  840.   tmp.tablenr=        table->tablenr;
  841.   tmp.tmp_table=    table->tmp_table;
  842.   tmp.used_fields=    table->used_fields;
  843.   tmp.const_table=    table->const_table;
  844.   tmp.outer_join=    table->outer_join;
  845.   tmp.null_row=        table->null_row;
  846.   tmp.status=        table->status;
  847.   tmp.grant=        table->grant;
  848.  
  849.   if (table->file)
  850.     VOID(closefrm(table));        // close file, free everything
  851.  
  852.   *table=tmp;
  853.   table->file->change_table_ptr(table);
  854.  
  855.   for (field=table->field ; *field ; field++)
  856.   {
  857.     (*field)->table=table;
  858.     (*field)->table_name=table->table_name;
  859.   }
  860.   for (key=0 ; key < table->keys ; key++)
  861.     for (part=0 ; part < table->key_info[key].usable_key_parts ; part++)
  862.       table->key_info[key].key_part[part].field->table=table;
  863.   VOID(pthread_cond_broadcast(&COND_refresh));
  864.   error=0;
  865.  
  866.  end:
  867.   if (!locked)
  868.     VOID(pthread_mutex_unlock(&LOCK_open));
  869.   DBUG_RETURN(error);
  870. }
  871.  
  872.  
  873. /*
  874.   Used with ALTER TABLE:
  875.   Close all instanses of table when LOCK TABLES is in used;
  876.   Close first all instances of table and then reopen them
  877.  */
  878.  
  879. bool close_data_tables(THD *thd,const char *db, const char *table_name)
  880. {
  881.   TABLE *table;
  882.   for (table=thd->open_tables; table ; table=table->next)
  883.   {
  884.     if (!strcmp(table->real_name,table_name) &&
  885.     !strcmp(table->table_cache_key,db))
  886.     {
  887.       mysql_lock_remove(thd, thd->locked_tables,table);
  888.       table->file->close();
  889.       table->db_stat=0;
  890.     }
  891.   }
  892.   return 0;                    // For the future
  893. }
  894.  
  895.  
  896. /*
  897.   Reopen all tables with closed data files
  898.   One should have lock on LOCK_open when calling this
  899. */
  900.  
  901. bool reopen_tables(THD *thd,bool get_locks,bool in_refresh)
  902. {
  903.   DBUG_ENTER("reopen_tables");
  904.   if (!thd->open_tables)
  905.     DBUG_RETURN(0);
  906.  
  907.   TABLE *table,*next,**prev;
  908.   TABLE **tables,**tables_ptr;            // For locks
  909.   bool error=0;
  910.   if (get_locks)
  911.   {
  912.     /* The ptr is checked later */
  913.     uint opens=0;
  914.     for (table=thd->open_tables; table ; table=table->next) opens++;
  915.     tables= (TABLE**) my_alloca(sizeof(TABLE*)*opens);
  916.   }
  917.   else
  918.     tables= &thd->open_tables;
  919.   tables_ptr =tables;
  920.  
  921.   prev= &thd->open_tables;
  922.   for (table=thd->open_tables; table ; table=next)
  923.   {
  924.     uint db_stat=table->db_stat;
  925.     next=table->next;
  926.     if (!tables || (!db_stat && reopen_table(table,1)))
  927.     {
  928.       my_error(ER_CANT_REOPEN_TABLE,MYF(0),table->table_name);
  929.       VOID(hash_delete(&open_cache,(byte*) table));
  930.       error=1;
  931.     }
  932.     else
  933.     {
  934.       *prev= table;
  935.       prev= &table->next;
  936.       if (get_locks && !db_stat)
  937.     *tables_ptr++= table;            // need new lock on this
  938.       if (in_refresh)
  939.       {
  940.     table->version=0;
  941.     table->locked_by_flush=0;
  942.       }
  943.     }
  944.   }
  945.   if (tables != tables_ptr)            // Should we get back old locks
  946.   {
  947.     MYSQL_LOCK *lock;
  948.     /* We should always get these locks */
  949.     thd->some_tables_deleted=0;
  950.     if ((lock=mysql_lock_tables(thd,tables,(uint) (tables_ptr-tables))))
  951.     {
  952.       thd->locked_tables=mysql_lock_merge(thd->locked_tables,lock);
  953.     }
  954.     else
  955.       error=1;
  956.   }
  957.   if (get_locks && tables)
  958.   {
  959.     my_afree((gptr) tables);
  960.   }
  961.   VOID(pthread_cond_broadcast(&COND_refresh)); // Signal to refresh
  962.   *prev=0;
  963.   DBUG_RETURN(error);
  964. }
  965.  
  966. /*
  967.   Close handlers for tables in list, but leave the TABLE structure
  968.   intact so that we can re-open these quickly
  969.   abort_locks is set if called from flush_tables.
  970. */
  971.  
  972. void close_old_data_files(THD *thd, TABLE *table, bool abort_locks,
  973.               bool send_refresh)
  974. {
  975.   DBUG_ENTER("close_old_data_files");
  976.   bool found=send_refresh;
  977.   for (; table ; table=table->next)
  978.   {
  979.     if (table->version != refresh_version)
  980.     {
  981.       found=1;
  982.       if (!abort_locks)                // If not from flush tables
  983.     table->version = refresh_version;    // Let other threads use table
  984.       if (table->db_stat)
  985.       {
  986.     if (abort_locks)
  987.     {
  988.       mysql_lock_abort(thd,table);        // Close waiting threads
  989.       mysql_lock_remove(thd, thd->locked_tables,table);
  990.       table->locked_by_flush=1;        // Will be reopened with locks
  991.     }
  992.     table->file->close();
  993.     table->db_stat=0;
  994.       }
  995.     }
  996.   }
  997.   if (found)
  998.     VOID(pthread_cond_broadcast(&COND_refresh)); // Signal to refresh
  999.   DBUG_VOID_RETURN;
  1000. }
  1001.  
  1002.  
  1003. /*
  1004.   Wait until all threads has closed the tables in the list
  1005.   We have also to wait if there is thread that has a lock on this table even
  1006.   if the table is closed
  1007. */
  1008.  
  1009. bool table_is_used(TABLE *table, bool wait_for_name_lock)
  1010. {
  1011.   do
  1012.   {
  1013.     char *key= table->table_cache_key;
  1014.     uint key_length=table->key_length;
  1015.     for (TABLE *search=(TABLE*) hash_search(&open_cache,
  1016.                         (byte*) key,key_length) ;
  1017.      search ;
  1018.      search = (TABLE*) hash_next(&open_cache,(byte*) key,key_length))
  1019.     {
  1020.       if (search->locked_by_flush ||
  1021.       search->locked_by_name && wait_for_name_lock ||
  1022.       search->db_stat && search->version < refresh_version)
  1023.     return 1;                // Table is used
  1024.     }
  1025.   } while ((table=table->next));
  1026.   return 0;
  1027. }
  1028.  
  1029.  
  1030. /* Wait until all used tables are refreshed */
  1031.  
  1032. bool wait_for_tables(THD *thd)
  1033. {
  1034.   bool result;
  1035.   DBUG_ENTER("wait_for_tables");
  1036.  
  1037.   thd->proc_info="Waiting for tables";
  1038.   pthread_mutex_lock(&LOCK_open);
  1039.   while (!thd->killed)
  1040.   {
  1041.     thd->some_tables_deleted=0;
  1042.     close_old_data_files(thd,thd->open_tables,0,dropping_tables != 0);
  1043.     if (!table_is_used(thd->open_tables,1))
  1044.       break;
  1045.     (void) pthread_cond_wait(&COND_refresh,&LOCK_open);    
  1046.   }
  1047.   if (thd->killed)
  1048.     result= 1;                    // aborted
  1049.   else
  1050.   {
  1051.     /* Now we can open all tables without any interference */
  1052.     thd->proc_info="Reopen tables";
  1053.     result=reopen_tables(thd,0,0);
  1054.   }
  1055.   pthread_mutex_unlock(&LOCK_open);
  1056.   thd->proc_info=0;
  1057.   DBUG_RETURN(result);
  1058. }
  1059.  
  1060.  
  1061. /* drop tables from locked list */
  1062.  
  1063. bool drop_locked_tables(THD *thd,const char *db, const char *table_name)
  1064. {
  1065.   TABLE *table,*next,**prev;
  1066.   bool found=0;
  1067.   prev= &thd->open_tables;
  1068.   for (table=thd->open_tables; table ; table=next)
  1069.   {
  1070.     next=table->next;
  1071.     if (!strcmp(table->real_name,table_name) &&
  1072.     !strcmp(table->table_cache_key,db))
  1073.     {
  1074.       mysql_lock_remove(thd, thd->locked_tables,table);
  1075.       VOID(hash_delete(&open_cache,(byte*) table));
  1076.       found=1;
  1077.     }
  1078.     else
  1079.     {
  1080.       *prev=table;
  1081.       prev= &table->next;
  1082.     }
  1083.   }
  1084.   *prev=0;
  1085.   if (found)
  1086.     VOID(pthread_cond_broadcast(&COND_refresh)); // Signal to refresh
  1087.   if (thd->locked_tables && thd->locked_tables->table_count == 0)
  1088.   {
  1089.     my_free((gptr) thd->locked_tables,MYF(0));
  1090.     thd->locked_tables=0;
  1091.   }
  1092.   return found;
  1093. }
  1094.  
  1095.  
  1096. /* lock table to force abort of any threads trying to use table */
  1097.  
  1098. void abort_locked_tables(THD *thd,const char *db, const char *table_name)
  1099. {
  1100.   TABLE *table;
  1101.   for (table=thd->open_tables; table ; table=table->next)
  1102.   {
  1103.     if (!strcmp(table->real_name,table_name) &&
  1104.     !strcmp(table->table_cache_key,db))
  1105.       mysql_lock_abort(thd,table);
  1106.   }
  1107. }
  1108.  
  1109. /****************************************************************************
  1110. **    open_unireg_entry
  1111. **    Purpose : Load a table definition from file and open unireg table
  1112. **    Args    : entry with DB and table given
  1113. **    Returns : 0 if ok
  1114. **    Note that the extra argument for open is taken from thd->open_options
  1115. */
  1116.  
  1117. static int open_unireg_entry(THD *thd, TABLE *entry, const char *db,
  1118.                  const char *name, const char *alias, bool locked)
  1119. {
  1120.   char path[FN_REFLEN];
  1121.   int error;
  1122.   DBUG_ENTER("open_unireg_entry");
  1123.  
  1124.   (void) sprintf(path,"%s/%s/%s",mysql_data_home,db,name);
  1125.   if (openfrm(path,alias,
  1126.            (uint) (HA_OPEN_KEYFILE | HA_OPEN_RNDFILE | HA_GET_INDEX |
  1127.                HA_TRY_READ_ONLY),
  1128.            READ_KEYINFO | COMPUTE_TYPES | EXTRA_RECORD,
  1129.           thd->open_options, entry))
  1130.   {
  1131.     if (!entry->crashed)
  1132.       goto err;                    // Can't repair the table
  1133.  
  1134.     TABLE_LIST table_list;
  1135.     table_list.db=(char*) db;
  1136.     table_list.name=(char*) name;
  1137.     table_list.next=0;
  1138.     if (!locked)
  1139.       pthread_mutex_lock(&LOCK_open);
  1140.     if ((error=lock_table_name(thd,&table_list)))
  1141.     {
  1142.       if (error < 0)
  1143.       {
  1144.     if (!locked)
  1145.       pthread_mutex_lock(&LOCK_open);
  1146.     goto err;
  1147.       }
  1148.       if (wait_for_locked_table_names(thd,&table_list))
  1149.       {
  1150.     unlock_table_name(thd,&table_list);
  1151.     if (!locked)
  1152.       pthread_mutex_lock(&LOCK_open);
  1153.     goto err;
  1154.       }
  1155.     }
  1156.     pthread_mutex_unlock(&LOCK_open);
  1157.     thd->net.last_error[0]=0;                // Clear error message
  1158.     thd->net.last_errno=0;
  1159.     error=0;
  1160.     if (openfrm(path,alias,
  1161.         (uint) (HA_OPEN_KEYFILE | HA_OPEN_RNDFILE | HA_GET_INDEX |
  1162.              HA_TRY_READ_ONLY),
  1163.         READ_KEYINFO | COMPUTE_TYPES | EXTRA_RECORD,
  1164.         ha_open_options | HA_OPEN_FOR_REPAIR,
  1165.         entry) || ! entry->file || 
  1166.     (entry->file->is_crashed() && entry->file->check_and_repair(thd)))
  1167.     {
  1168.       /* Give right error message */
  1169.       thd->net.last_error[0]=0;
  1170.       thd->net.last_errno=0;
  1171.       my_error(ER_NOT_KEYFILE, MYF(0), name, my_errno);
  1172.       sql_print_error("Error: Couldn't repair table: %s.%s",db,name);
  1173.       if (entry->file)
  1174.     closefrm(entry);
  1175.       error=1;
  1176.     }
  1177.     else
  1178.     {
  1179.       thd->net.last_error[0]=0;            // Clear error message
  1180.       thd->net.last_errno=0;
  1181.     }
  1182.     if (locked)
  1183.       pthread_mutex_lock(&LOCK_open);      // Get back original lock
  1184.     unlock_table_name(thd,&table_list);
  1185.     if (error)
  1186.       goto err;
  1187.   }
  1188.   (void) entry->file->extra(HA_EXTRA_NO_READCHECK);    // Not needed in SQL
  1189.   DBUG_RETURN(0);
  1190. err:
  1191.   DBUG_RETURN(1);
  1192. }
  1193.  
  1194.  
  1195. /*****************************************************************************
  1196. ** open all tables in list
  1197. *****************************************************************************/
  1198.  
  1199. int open_tables(THD *thd,TABLE_LIST *start)
  1200. {
  1201.   TABLE_LIST *tables;
  1202.   bool refresh;
  1203.   int result=0;
  1204.   DBUG_ENTER("open_tables");
  1205.  
  1206.  restart:
  1207.   thd->proc_info="Opening tables";
  1208.   for (tables=start ; tables ; tables=tables->next)
  1209.   {
  1210.     if (!tables->table &&
  1211.     !(tables->table=open_table(thd,
  1212.                    tables->db ? tables->db : thd->db,
  1213.                    tables->real_name,
  1214.                    tables->name, &refresh)))
  1215.     {
  1216.       if (refresh)                // Refresh in progress
  1217.       {
  1218.     /* close all 'old' tables used by this thread */
  1219.     pthread_mutex_lock(&LOCK_open);
  1220.     thd->version=refresh_version;
  1221.     TABLE **prev_table= &thd->open_tables;
  1222.     bool found=0;
  1223.     for (TABLE_LIST *tmp=start ; tmp ; tmp=tmp->next)
  1224.     {
  1225.       if (tmp->table)
  1226.       {
  1227.         if (tmp->table->version != refresh_version ||
  1228.         ! tmp->table->db_stat)
  1229.         {
  1230.           VOID(hash_delete(&open_cache,(byte*) tmp->table));
  1231.           tmp->table=0;
  1232.           found=1;
  1233.         }
  1234.         else
  1235.         {
  1236.           *prev_table= tmp->table;        // Relink open list
  1237.           prev_table= &tmp->table->next;
  1238.         }
  1239.       }
  1240.     }
  1241.     *prev_table=0;
  1242.     if (found)
  1243.       VOID(pthread_cond_broadcast(&COND_refresh)); // Signal to refresh
  1244.     pthread_mutex_unlock(&LOCK_open);
  1245.     goto restart;
  1246.       }
  1247.       result= -1;                // Fatal error
  1248.       break;
  1249.     }
  1250.     if (tables->lock_type != TL_UNLOCK)
  1251.       tables->table->reginfo.lock_type=tables->lock_type;
  1252.     tables->table->grant= tables->grant;
  1253.   }
  1254.   thd->proc_info=0;
  1255.   DBUG_RETURN(result);
  1256. }
  1257.  
  1258.  
  1259. TABLE *open_ltable(THD *thd, TABLE_LIST *table_list, thr_lock_type lock_type)
  1260. {
  1261.   TABLE *table;
  1262.   bool refresh;
  1263.   DBUG_ENTER("open_ltable");
  1264.  
  1265. #ifdef __WIN__
  1266.   /* Win32 can't drop a file that is open */
  1267.   if (lock_type == TL_WRITE_ALLOW_READ)
  1268.     lock_type= TL_WRITE;
  1269. #endif
  1270.   thd->proc_info="Opening table";
  1271.   while (!(table=open_table(thd,table_list->db ? table_list->db : thd->db,
  1272.                 table_list->real_name,table_list->name,
  1273.                 &refresh)) && refresh) ;
  1274.   if (table)
  1275.   {
  1276.     table_list->table=table;
  1277.     table->grant= table_list->grant;
  1278.     if (thd->locked_tables)
  1279.     {
  1280.       thd->proc_info=0;
  1281.       if ((int) lock_type >= (int) TL_WRITE_ALLOW_READ &&
  1282.       (int) table->reginfo.lock_type < (int) TL_WRITE_ALLOW_READ)
  1283.       {
  1284.     my_printf_error(ER_TABLE_NOT_LOCKED_FOR_WRITE,
  1285.             ER(ER_TABLE_NOT_LOCKED_FOR_WRITE),
  1286.             MYF(0),table_list->name);
  1287.     DBUG_RETURN(0);
  1288.       }
  1289.       thd->proc_info=0;
  1290.       DBUG_RETURN(table);
  1291.     }
  1292.     if ((table->reginfo.lock_type=lock_type) != TL_UNLOCK)
  1293.       if (!(thd->lock=mysql_lock_tables(thd,&table_list->table,1)))
  1294.       DBUG_RETURN(0);
  1295.   }
  1296.   thd->proc_info=0;
  1297.   DBUG_RETURN(table);
  1298. }
  1299.  
  1300. /*
  1301. ** Open all tables in list and locks them for read.
  1302. ** The lock will automaticly be freed by the close_thread_tables
  1303. */
  1304.  
  1305. int open_and_lock_tables(THD *thd,TABLE_LIST *tables)
  1306. {
  1307.   if (open_tables(thd,tables) || lock_tables(thd,tables))
  1308.     return -1;                    /* purecov: inspected */
  1309.   return 0;
  1310. }
  1311.  
  1312. int lock_tables(THD *thd,TABLE_LIST *tables)
  1313. {
  1314.   if (tables && !thd->locked_tables)
  1315.   {
  1316.     uint count=0;
  1317.     TABLE_LIST *table;
  1318.     for (table = tables ; table ; table=table->next)
  1319.       count++;
  1320.     TABLE **start,**ptr;
  1321.     if (!(ptr=start=(TABLE**) sql_alloc(sizeof(TABLE*)*count)))
  1322.       return -1;
  1323.     for (table = tables ; table ; table=table->next)
  1324.       *(ptr++)= table->table;
  1325.     if (!(thd->lock=mysql_lock_tables(thd,start,count)))
  1326.       return -1;                /* purecov: inspected */
  1327.   }
  1328.   return 0;
  1329. }
  1330.  
  1331. /*
  1332. ** Open a single table without table caching and don't set it in open_list
  1333. ** Used by alter_table to open a temporary table and when creating
  1334. ** a temporary table with CREATE TEMPORARY ...
  1335. */
  1336.  
  1337. TABLE *open_temporary_table(THD *thd, const char *path, const char *db,
  1338.                 const char *table_name, bool link_in_list)
  1339. {
  1340.   TABLE *tmp_table;
  1341.   DBUG_ENTER("open_temporary_table");
  1342.   if (!(tmp_table=(TABLE*) my_malloc(sizeof(*tmp_table)+(uint) strlen(db)+
  1343.                      (uint) strlen(table_name)+2,
  1344.                      MYF(MY_WME))))
  1345.     DBUG_RETURN(0);                /* purecov: inspected */
  1346.  
  1347.   if (openfrm(path, table_name,
  1348.           (uint) (HA_OPEN_KEYFILE | HA_OPEN_RNDFILE | HA_GET_INDEX |
  1349.               HA_TRY_READ_ONLY),
  1350.           READ_KEYINFO | COMPUTE_TYPES | EXTRA_RECORD,
  1351.           ha_open_options,
  1352.           tmp_table))
  1353.   {
  1354.     DBUG_RETURN(0);
  1355.   }
  1356.  
  1357.   tmp_table->file->extra(HA_EXTRA_NO_READCHECK); // Not needed in SQL
  1358.   tmp_table->reginfo.lock_type=TL_WRITE;    // Simulate locked
  1359.   tmp_table->tmp_table = 1;
  1360.   tmp_table->table_cache_key=(char*) (tmp_table+1);
  1361.   tmp_table->key_length= (uint) (strmov(strmov(tmp_table->table_cache_key,db)
  1362.                     +1, table_name)
  1363.                  - tmp_table->table_cache_key)+1;
  1364.   if (link_in_list)
  1365.   {
  1366.     tmp_table->next=thd->temporary_tables;
  1367.     thd->temporary_tables=tmp_table;
  1368.   }
  1369.   DBUG_RETURN(tmp_table);
  1370. }
  1371.  
  1372.  
  1373. bool rm_temporary_table(enum db_type base, char *path)
  1374. {
  1375.   bool error=0;
  1376.   fn_format(path, path,"",reg_ext,4);
  1377.   unpack_filename(path,path);
  1378.   if (my_delete(path,MYF(0)))
  1379.     error=1; /* purecov: inspected */
  1380.   *fn_ext(path)='\0';                // remove extension
  1381.   handler *file=get_new_handler((TABLE*) 0, base);
  1382.   if (file && file->delete_table(path))
  1383.     error=1;
  1384.   delete file;
  1385.   return error;
  1386. }
  1387.  
  1388.  
  1389. /*****************************************************************************
  1390. ** find field in list or tables. if field is unqualifed and unique,
  1391. ** return unique field
  1392. ******************************************************************************/
  1393.  
  1394. #define WRONG_GRANT (Field*) -1
  1395.  
  1396. Field *find_field_in_table(THD *thd,TABLE *table,const char *name,uint length,
  1397.                bool check_grants, bool allow_rowid)
  1398. {
  1399.   Field *field;
  1400.   if (table->name_hash.records)
  1401.   {
  1402.     if ((field=(Field*) hash_search(&table->name_hash,(byte*) name,
  1403.                     length)))
  1404.       goto found;
  1405.   }
  1406.   else
  1407.   {
  1408.     Field **ptr=table->field;
  1409.     while ((field = *ptr++))
  1410.     {
  1411.       if (!my_strcasecmp(field->field_name, name))
  1412.     goto found;
  1413.     }
  1414.   }
  1415.   if (allow_rowid && !my_strcasecmp(name,"_rowid") &&
  1416.       (field=table->rowid_field))
  1417.     goto found;
  1418.   return (Field*) 0;
  1419.  
  1420.  found:
  1421.   if (thd->set_query_id)
  1422.   {
  1423.     if (field->query_id != thd->query_id)
  1424.     {
  1425.       field->query_id=thd->query_id;
  1426.       table->used_fields++;
  1427.       if (field->part_of_key)
  1428.       {
  1429.     if (!(field->part_of_key & table->ref_primary_key))
  1430.       table->used_keys&=field->part_of_key;
  1431.       }
  1432.       else
  1433.     table->used_keys=0;
  1434.     }
  1435.     else
  1436.       thd->dupp_field=field;
  1437.   }
  1438.   if (check_grants && !thd->master_access && check_grant_column(thd,table,name,length))
  1439.     return WRONG_GRANT;
  1440.   return field;
  1441. }
  1442.  
  1443.  
  1444. Field *
  1445. find_field_in_tables(THD *thd,Item_field *item,TABLE_LIST *tables)
  1446. {
  1447.   Field *found=0;
  1448.   const char *db=item->db_name;
  1449.   const char *table_name=item->table_name;
  1450.   const char *name=item->field_name;
  1451.   uint length=(uint) strlen(name);
  1452.  
  1453.   if (table_name)
  1454.   {                        /* Qualified field */
  1455.     bool found_table=0;
  1456.     for (; tables ; tables=tables->next)
  1457.     {
  1458.       if (!strcmp(tables->name,table_name) &&
  1459.       (!db ||
  1460.        (tables->db && !strcmp(db,tables->db)) ||
  1461.        (!tables->db && !strcmp(db,thd->db))))
  1462.       {
  1463.     found_table=1;
  1464.     Field *find=find_field_in_table(thd,tables->table,name,length,
  1465.                     grant_option && !thd->master_access,1);
  1466.     if (find)
  1467.     {
  1468.       if (find == WRONG_GRANT)
  1469.         return (Field*) 0;
  1470.       if (db || !thd->where)
  1471.         return find;
  1472.       if (found)
  1473.       {
  1474.         my_printf_error(ER_NON_UNIQ_ERROR,ER(ER_NON_UNIQ_ERROR),MYF(0),
  1475.                 item->full_name(),thd->where);
  1476.         return (Field*) 0;
  1477.       }
  1478.       found=find;
  1479.     }
  1480.       }
  1481.     }
  1482.     if (found)
  1483.       return found;
  1484.     if (!found_table)
  1485.     {
  1486.       char buff[NAME_LEN*2+1];
  1487.       if (db)
  1488.       {
  1489.     strxmov(buff,db,".",table_name,NullS);
  1490.     table_name=buff;
  1491.       }
  1492.       my_printf_error(ER_UNKNOWN_TABLE,ER(ER_UNKNOWN_TABLE),MYF(0),table_name,
  1493.               thd->where);
  1494.     }
  1495.     else
  1496.       my_printf_error(ER_BAD_FIELD_ERROR,ER(ER_BAD_FIELD_ERROR),MYF(0),
  1497.               item->full_name(),thd->where);
  1498.     return (Field*) 0;
  1499.   }
  1500.   bool allow_rowid= tables && !tables->next;    // Only one table
  1501.   for (; tables ; tables=tables->next)
  1502.   {
  1503.     Field *field=find_field_in_table(thd,tables->table,name,length,
  1504.                      grant_option && !thd->master_access, allow_rowid);
  1505.     if (field)
  1506.     {
  1507.       if (field == WRONG_GRANT)
  1508.     return (Field*) 0;
  1509.       if (found)
  1510.       {
  1511.     if (!thd->where)            // Returns first found
  1512.       break;
  1513.     my_printf_error(ER_NON_UNIQ_ERROR,ER(ER_NON_UNIQ_ERROR),MYF(0),
  1514.             name,thd->where);
  1515.     return (Field*) 0;
  1516.       }
  1517.       found=field;
  1518.     }
  1519.   }
  1520.   if (found)
  1521.     return found;
  1522.   my_printf_error(ER_BAD_FIELD_ERROR,ER(ER_BAD_FIELD_ERROR),
  1523.           MYF(0),item->full_name(),thd->where);
  1524.   return (Field*) 0;
  1525. }
  1526.  
  1527. Item **
  1528. find_item_in_list(Item *find,List<Item> &items)
  1529. {
  1530.   List_iterator<Item> li(items);
  1531.   Item **found=0,*item;
  1532.   const char *field_name=0;
  1533.   const char *table_name=0;
  1534.   if (find->type() == Item::FIELD_ITEM    || find->type() == Item::REF_ITEM)
  1535.   {
  1536.     field_name= ((Item_ident*) find)->field_name;
  1537.     table_name= ((Item_ident*) find)->table_name;
  1538.   }
  1539.  
  1540.   while ((item=li++))
  1541.   {
  1542.     if (field_name && item->type() == Item::FIELD_ITEM)
  1543.     {
  1544.       if (!my_strcasecmp(((Item_field*) item)->name,field_name))
  1545.       {
  1546.     if (!table_name)
  1547.     {
  1548.       if (found)
  1549.       {
  1550.         if ((*found)->eq(item))
  1551.           continue;                // Same field twice (Access?)
  1552.         if (current_thd->where)
  1553.           my_printf_error(ER_NON_UNIQ_ERROR,ER(ER_NON_UNIQ_ERROR),MYF(0),
  1554.                   find->full_name(), current_thd->where);
  1555.         return (Item**) 0;
  1556.       }
  1557.       found=li.ref();
  1558.     }
  1559.     else if (!strcmp(((Item_field*) item)->table_name,table_name))
  1560.     {
  1561.       found=li.ref();
  1562.       break;
  1563.     }
  1564.       }
  1565.     }
  1566.     else if (!table_name && (item->eq(find) ||
  1567.                  find->name &&
  1568.                  !my_strcasecmp(item->name,find->name)))
  1569.     {
  1570.       found=li.ref();
  1571.       break;
  1572.     }
  1573.   }
  1574.   if (!found && current_thd->where)
  1575.     my_printf_error(ER_BAD_FIELD_ERROR,ER(ER_BAD_FIELD_ERROR),MYF(0),
  1576.             find->full_name(),current_thd->where);
  1577.   return found;
  1578. }
  1579.  
  1580.  
  1581. /****************************************************************************
  1582. ** Check that all given fields exists and fill struct with current data
  1583. ** Check also that the 'used keys' and 'ignored keys' exists and set up the
  1584. ** table structure accordingly
  1585. ****************************************************************************/
  1586.  
  1587. int setup_fields(THD *thd, TABLE_LIST *tables, List<Item> &fields,
  1588.          bool set_query_id, List<Item> *sum_func_list)
  1589. {
  1590.   reg2 Item *item;
  1591.   List_iterator<Item> it(fields);
  1592.   DBUG_ENTER("setup_fields");
  1593.  
  1594.   thd->set_query_id=set_query_id;
  1595.   thd->allow_sum_func= test(sum_func_list);
  1596.   thd->where="field list";
  1597.  
  1598.   /* Remap table numbers if INSERT ... SELECT */
  1599.   uint tablenr=0;
  1600.   for (TABLE_LIST *table=tables ; table ; table=table->next,tablenr++)
  1601.   {
  1602.     table->table->tablenr=tablenr;
  1603.     table->table->map= (table_map) 1 << tablenr;
  1604.     if ((table->table->outer_join=table->outer_join))
  1605.       table->table->maybe_null=1;        // LEFT OUTER JOIN ...
  1606.     if (table->use_index)
  1607.     {
  1608.       key_map map= get_key_map_from_key_list(thd,table->table,
  1609.                          table->use_index);
  1610.       if (map == ~(key_map) 0)
  1611.     DBUG_RETURN(-1);
  1612.       table->table->keys_in_use_for_query=map;
  1613.     }
  1614.     if (table->ignore_index)
  1615.     {
  1616.       key_map map= get_key_map_from_key_list(thd,table->table,
  1617.                          table->ignore_index);
  1618.       if (map == ~(key_map) 0)
  1619.     DBUG_RETURN(-1);
  1620.       table->table->keys_in_use_for_query &= ~map;
  1621.     }
  1622.   }
  1623.   if (tablenr > MAX_TABLES)
  1624.   {
  1625.     my_error(ER_TOO_MANY_TABLES,MYF(0),MAX_TABLES);
  1626.     DBUG_RETURN(-1);
  1627.   }
  1628.   while ((item=it++))
  1629.   {
  1630.     if (item->type() == Item::FIELD_ITEM &&
  1631.     ((Item_field*) item)->field_name[0] == '*')
  1632.     {
  1633.       if (insert_fields(thd,tables,((Item_field*) item)->table_name,&it))
  1634.     DBUG_RETURN(-1); /* purecov: inspected */
  1635.     }
  1636.     else
  1637.     {
  1638.       if (item->fix_fields(thd,tables))
  1639.     DBUG_RETURN(-1); /* purecov: inspected */
  1640.       if (item->with_sum_func && item->type() != Item::SUM_FUNC_ITEM)
  1641.     item->split_sum_func(*sum_func_list);
  1642.       thd->used_tables|=item->used_tables();
  1643.     }
  1644.   }
  1645.   DBUG_RETURN(test(thd->fatal_error));
  1646. }
  1647.  
  1648.  
  1649. static key_map get_key_map_from_key_list(THD *thd, TABLE *table,
  1650.                      List<String> *index_list)
  1651. {
  1652.   key_map map=0;
  1653.   List_iterator<String> it(*index_list);
  1654.   String *name;
  1655.   uint pos;
  1656.   while ((name=it++))
  1657.   {
  1658.     if ((pos=find_type(name->c_ptr(), &table->keynames, 1)) <= 0)
  1659.     {
  1660.       my_error(ER_KEY_COLUMN_DOES_NOT_EXITS, MYF(0), name->c_ptr(),
  1661.            table->real_name);
  1662.       return (~ (key_map) 0);
  1663.     }
  1664.     map|= ((key_map) 1) << (pos-1);
  1665.   }
  1666.   return map;
  1667. }
  1668.  
  1669. /****************************************************************************
  1670. **    This just drops in all fields instead of current '*' field
  1671. **    Returns pointer to last inserted field if ok
  1672. ****************************************************************************/
  1673.  
  1674. static bool
  1675. insert_fields(THD *thd,TABLE_LIST *tables, const char *table_name,
  1676.           List_iterator<Item> *it)
  1677. {
  1678.   uint found;
  1679.   DBUG_ENTER("insert_fields");
  1680.  
  1681.   found=0;
  1682.   for (; tables ; tables=tables->next)
  1683.   {
  1684.     TABLE *table=tables->table;
  1685.     if (grant_option && !thd->master_access &&
  1686.     check_grant_all_columns(thd,SELECT_ACL,table) )
  1687.       DBUG_RETURN(-1);
  1688.     if (!table_name || !strcmp(table_name,tables->name))
  1689.     {
  1690.       Field **ptr=table->field,*field;
  1691.       thd->used_tables|=table->map;
  1692.       while ((field = *ptr++))
  1693.       {
  1694.     Item_field *item= new Item_field(field);
  1695.     if (!found++)
  1696.       (void) it->replace(item);
  1697.     else
  1698.       it->after(item);
  1699.     if (field->query_id == thd->query_id)
  1700.       thd->dupp_field=field;
  1701.     field->query_id=thd->query_id;
  1702.  
  1703.     if (field->part_of_key)
  1704.     {
  1705.       if (!(field->part_of_key & table->ref_primary_key))
  1706.         table->used_keys&=field->part_of_key;
  1707.     }
  1708.     else
  1709.       table->used_keys=0;
  1710.       }
  1711.       /* All fields are used */
  1712.       table->used_fields=table->fields;
  1713.     }
  1714.   }
  1715.   if (!found)
  1716.   {
  1717.     if (!table_name)
  1718.       my_error(ER_NO_TABLES_USED,MYF(0));
  1719.     else
  1720.       my_error(ER_BAD_TABLE_ERROR,MYF(0),table_name);
  1721.   }
  1722.   DBUG_RETURN(!found);
  1723. }
  1724.  
  1725.  
  1726. /*
  1727. ** Fix all conditions and outer join expressions
  1728. */
  1729.  
  1730. int setup_conds(THD *thd,TABLE_LIST *tables,COND **conds)
  1731. {
  1732.   DBUG_ENTER("setup_conds");
  1733.   thd->set_query_id=1;
  1734.   thd->cond_count=0;
  1735.   thd->allow_sum_func=0;
  1736.   if (*conds)
  1737.   {
  1738.     thd->where="where clause";
  1739.     if ((*conds)->fix_fields(thd,tables))
  1740.       DBUG_RETURN(1);
  1741.   }
  1742.  
  1743.   /* Check if we are using outer joins */
  1744.   for (TABLE_LIST *table=tables ; table ; table=table->next)
  1745.   {
  1746.     if (table->on_expr)
  1747.     {
  1748.       /* Make a join an a expression */
  1749.       thd->where="on clause";
  1750.       if (table->on_expr->fix_fields(thd,tables))
  1751.     DBUG_RETURN(1);
  1752.       thd->cond_count++;
  1753.  
  1754.       /* If it's a normal join, add the ON/USING expression to the WHERE */
  1755.       if (!table->outer_join)
  1756.       {
  1757.     if (!(*conds=and_conds(*conds, table->on_expr)))
  1758.       DBUG_RETURN(1);
  1759.     table->on_expr=0;
  1760.       }
  1761.     }
  1762.     if (table->natural_join)
  1763.     {
  1764.       /* Make a join of all fields with have the same name */
  1765.       TABLE *t1=table->table;
  1766.       TABLE *t2=table->natural_join->table;
  1767.       Item_cond_and *cond_and=new Item_cond_and();
  1768.       if (!cond_and)                // If not out of memory
  1769.     DBUG_RETURN(1);
  1770.  
  1771.       uint i,j;
  1772.       for (i=0 ; i < t1->fields ; i++)
  1773.       {
  1774.     // TODO: This could be optimized to use hashed names if t2 had a hash
  1775.     for (j=0 ; j < t2->fields ; j++)
  1776.     {
  1777.       key_map tmp_map;
  1778.       if (!my_strcasecmp(t1->field[i]->field_name,
  1779.                  t2->field[j]->field_name))
  1780.       {
  1781.         Item_func_eq *tmp=new Item_func_eq(new Item_field(t1->field[i]),
  1782.                            new Item_field(t2->field[j]));
  1783.         if (!tmp)
  1784.           DBUG_RETURN(1);
  1785.         tmp->fix_length_and_dec();    // Update cmp_type
  1786.         tmp->const_item_cache=0;
  1787.         /* Mark field used for table cache */
  1788.         t1->field[i]->query_id=t2->field[j]->query_id=thd->query_id;
  1789.         cond_and->list.push_back(tmp);
  1790.         if ((tmp_map=t1->field[i]->part_of_key))
  1791.         {
  1792.           if (!(tmp_map & t1->ref_primary_key))
  1793.         t1->used_keys&=tmp_map;
  1794.         }
  1795.         else
  1796.           t1->used_keys=0;
  1797.         if ((tmp_map=t2->field[j]->part_of_key))
  1798.         {
  1799.           if (!(tmp_map & t2->ref_primary_key))
  1800.         t2->used_keys&=tmp_map;
  1801.         }
  1802.         else
  1803.           t2->used_keys=0;
  1804.         break;
  1805.       }
  1806.     }
  1807.       }
  1808.       cond_and->used_tables_cache= t1->map | t2->map;
  1809.       thd->cond_count+=cond_and->list.elements;
  1810.       if (!table->outer_join)            // Not left join
  1811.       {
  1812.     if (!(*conds=and_conds(*conds, cond_and)))
  1813.       DBUG_RETURN(1);
  1814.       }
  1815.       else
  1816.     table->on_expr=and_conds(table->on_expr,cond_and);
  1817.     }
  1818.   }
  1819.   DBUG_RETURN(test(thd->fatal_error));
  1820. }
  1821.  
  1822.  
  1823. /******************************************************************************
  1824. ** Fill a record with data (for INSERT or UPDATE)
  1825. ** Returns : 1 if some field has wrong type
  1826. ******************************************************************************/
  1827.  
  1828. int
  1829. fill_record(List<Item> &fields,List<Item> &values)
  1830. {
  1831.   List_iterator<Item> f(fields),v(values);
  1832.   Item *value;
  1833.   Item_field *field;
  1834.   DBUG_ENTER("fill_record");
  1835.  
  1836.   while ((field=(Item_field*) f++))
  1837.   {
  1838.     value=v++;
  1839.     if (value->save_in_field(field->field))
  1840.       DBUG_RETURN(1);
  1841.   }
  1842.   DBUG_RETURN(0);
  1843. }
  1844.  
  1845.  
  1846. int
  1847. fill_record(Field **ptr,List<Item> &values)
  1848. {
  1849.   List_iterator<Item> v(values);
  1850.   Item *value;
  1851.   DBUG_ENTER("fill_record");
  1852.  
  1853.   Field *field;
  1854.   while ((field = *ptr++))
  1855.   {
  1856.     value=v++;
  1857.     if (value->save_in_field(field))
  1858.       DBUG_RETURN(1);
  1859.   }
  1860.   DBUG_RETURN(0);
  1861. }
  1862.  
  1863.  
  1864. static void mysql_rm_tmp_tables(void)
  1865. {
  1866.   uint idx;
  1867.   char    filePath[FN_REFLEN];
  1868.   MY_DIR *dirp;
  1869.   FILEINFO *file;
  1870.   DBUG_ENTER("mysql_rm_tmp_tables");
  1871.  
  1872.   /* See if the directory exists */
  1873.   if (!(dirp = my_dir(mysql_tmpdir,MYF(MY_WME | MY_DONT_SORT))))
  1874.     DBUG_VOID_RETURN;                /* purecov: inspected */
  1875.  
  1876.   /*
  1877.   ** Remove all SQLxxx tables from directory
  1878.   */
  1879.  
  1880.   for (idx=2 ; idx < (uint) dirp->number_off_files ; idx++)
  1881.   {
  1882.     file=dirp->dir_entry+idx;
  1883.     if (!bcmp(file->name,tmp_file_prefix,tmp_file_prefix_length))
  1884.     {
  1885.       sprintf(filePath,"%s%s",mysql_tmpdir,file->name); /* purecov: inspected */
  1886.       VOID(my_delete(filePath,MYF(MY_WME)));    /* purecov: inspected */
  1887.     }
  1888.   }
  1889.   my_dirend(dirp);
  1890.   DBUG_VOID_RETURN;
  1891. }
  1892.  
  1893.  
  1894. /*
  1895. ** CREATE INDEX and DROP INDEX are implemented by calling ALTER TABLE with
  1896. ** the proper arguments.  This isn't very fast but it should work for most
  1897. ** cases.
  1898. ** One should normally create all indexes with CREATE TABLE or ALTER TABLE.
  1899. */
  1900.  
  1901. int mysql_create_index(THD *thd, TABLE_LIST *table_list, List<Key> &keys)
  1902. {
  1903.   List<create_field> fields;
  1904.   List<Alter_drop> drop;
  1905.   List<Alter_column> alter;
  1906.   HA_CREATE_INFO create_info;
  1907.   DBUG_ENTER("mysql_create_index");
  1908.   bzero((char*) &create_info,sizeof(create_info));
  1909.   create_info.db_type=DB_TYPE_DEFAULT;
  1910.   DBUG_RETURN(mysql_alter_table(thd,table_list->db,table_list->real_name,
  1911.                 &create_info, table_list,
  1912.                 fields, keys, drop, alter, (ORDER*)0, FALSE, DUP_ERROR));
  1913. }
  1914.  
  1915.  
  1916. int mysql_drop_index(THD *thd, TABLE_LIST *table_list, List<Alter_drop> &drop)
  1917. {
  1918.   List<create_field> fields;
  1919.   List<Key> keys;
  1920.   List<Alter_column> alter;
  1921.   HA_CREATE_INFO create_info;
  1922.   DBUG_ENTER("mysql_drop_index");
  1923.   bzero((char*) &create_info,sizeof(create_info));
  1924.   create_info.db_type=DB_TYPE_DEFAULT;
  1925.   DBUG_RETURN(mysql_alter_table(thd,table_list->db,table_list->real_name,
  1926.                 &create_info, table_list,
  1927.                 fields, keys, drop, alter, (ORDER*)0, FALSE, DUP_ERROR));
  1928. }
  1929.  
  1930. /*****************************************************************************
  1931.     unireg support functions
  1932. *****************************************************************************/
  1933.  
  1934. /*
  1935. ** Invalidate any cache entries that are for some DB
  1936. ** We can't use hash_delete when looping hash_elements. We mark them first
  1937. ** and afterwards delete those marked unused.
  1938. */
  1939.  
  1940. void remove_db_from_cache(const my_string db)
  1941. {
  1942.   for (uint idx=0 ; idx < open_cache.records ; idx++)
  1943.   {
  1944.     TABLE *table=(TABLE*) hash_element(&open_cache,idx);
  1945.     if (!strcmp(table->table_cache_key,db))
  1946.     {
  1947.       table->version=0L;            /* Free when thread is ready */
  1948.       if (!table->in_use)
  1949.     relink_unused(table);
  1950.     }
  1951.   }
  1952.   while (unused_tables && !unused_tables->version)
  1953.     VOID(hash_delete(&open_cache,(byte*) unused_tables));
  1954. }
  1955.  
  1956.  
  1957. /*
  1958. ** free all unused tables
  1959. */
  1960.  
  1961. void flush_tables()
  1962. {
  1963.   (void) pthread_mutex_lock(&LOCK_open);
  1964.   while (unused_tables)
  1965.     hash_delete(&open_cache,(byte*) unused_tables);
  1966.   (void) pthread_mutex_unlock(&LOCK_open);
  1967. }
  1968.  
  1969.  
  1970. /*
  1971. ** Mark all entries with the table as deleted to force an reopen of the table
  1972. ** Returns true if the table is in use by another thread
  1973. */
  1974.  
  1975. bool remove_table_from_cache(THD *thd, const char *db,const char *table_name)
  1976. {
  1977.   char key[MAX_DBKEY_LENGTH];
  1978.   uint key_length;
  1979.   TABLE *table;
  1980.   bool result=0;
  1981.   DBUG_ENTER("remove_table_from_cache");
  1982.  
  1983.   key_length=(uint) (strmov(strmov(key,db)+1,table_name)-key)+1;
  1984.   for (table=(TABLE*) hash_search(&open_cache,(byte*) key,key_length) ;
  1985.        table;
  1986.        table = (TABLE*) hash_next(&open_cache,(byte*) key,key_length))
  1987.   {
  1988.     table->version=0L;            /* Free when thread is ready */
  1989.     if (!table->in_use)
  1990.       relink_unused(table);
  1991.     else if (table->in_use != thd)
  1992.     {
  1993.       THD *in_use=table->in_use;
  1994.  
  1995.       in_use->some_tables_deleted=1;
  1996.       if (table->db_stat)
  1997.     result=1;
  1998.       /* Kill delayed insert threads */
  1999.       if (in_use->system_thread && ! in_use->killed)
  2000.       {
  2001.     in_use->killed=1;
  2002.     pthread_mutex_lock(&in_use->mysys_var->mutex);
  2003.     if (in_use->mysys_var->current_mutex)
  2004.     {
  2005.       pthread_mutex_lock(in_use->mysys_var->current_mutex);
  2006.       pthread_cond_broadcast(in_use->mysys_var->current_cond);
  2007.       pthread_mutex_unlock(in_use->mysys_var->current_mutex);
  2008.     }
  2009.     pthread_mutex_unlock(&in_use->mysys_var->mutex);
  2010.       }
  2011.     }
  2012.   }
  2013.   while (unused_tables && !unused_tables->version)
  2014.     VOID(hash_delete(&open_cache,(byte*) unused_tables));
  2015.   DBUG_RETURN(result);
  2016. }
  2017.  
  2018. int setup_ftfuncs(THD *thd,TABLE_LIST *tables, List<Item_func_match> &ftfuncs)
  2019. {
  2020.   List_iterator<Item_func_match> li(ftfuncs), li2(ftfuncs);
  2021.   Item_func_match *ftf, *ftf2;
  2022.  
  2023.   while ((ftf=li++))
  2024.   {
  2025.     if (ftf->fix_index())
  2026.       return 1;
  2027.     li2.rewind();
  2028.     while ((ftf2=li2++) != ftf)
  2029.     {
  2030.       if (ftf->eq(ftf2) && !ftf2->master)
  2031.         ftf2->master=ftf;
  2032.     }
  2033.   }
  2034.  
  2035.   return 0;
  2036. }
  2037.