~drizzle-trunk/drizzle/development

« back to all changes in this revision

Viewing changes to drizzled/sql_parse.cc

  • Committer: Brian Aker
  • Date: 2010-02-22 19:23:48 UTC
  • mfrom: (1273.13.95 build)
  • Revision ID: brian@gaz-20100222192348-bcda6uwqmyt30rbi
Merge Padraig.

Show diffs side-by-side

added added

removed removed

Lines of Context:
65
65
/* Prototypes */
66
66
bool my_yyoverflow(short **a, YYSTYPE **b, ulong *yystacksize);
67
67
static bool parse_sql(Session *session, Lex_input_stream *lip);
68
 
void mysql_parse(Session *session, const char *inBuf, uint32_t length,
69
 
                 const char ** found_semicolon);
 
68
void mysql_parse(Session *session, const char *inBuf, uint32_t length);
70
69
 
71
70
/**
72
71
  @defgroup Runtime_Environment Runtime Environment
212
211
  {
213
212
    if (! session->readAndStoreQuery(packet, packet_length))
214
213
      break;                                    // fatal error is set
215
 
    DRIZZLE_QUERY_START(session->query,
 
214
    DRIZZLE_QUERY_START(session->query.c_str(),
216
215
                        session->thread_id,
217
216
                        const_cast<const char *>(session->db.empty() ? "" : session->db.c_str()));
218
 
    const char* end_of_stmt= NULL;
219
217
 
220
 
    mysql_parse(session, session->query, session->query_length, &end_of_stmt);
 
218
    mysql_parse(session, session->query.c_str(), session->query.length());
221
219
 
222
220
    break;
223
221
  }
308
306
  session->set_proc_info("cleaning up");
309
307
  session->command= COM_SLEEP;
310
308
  memset(session->process_list_info, 0, PROCESS_LIST_WIDTH);
311
 
  session->query= 0;
312
 
  session->query_length= 0;
 
309
  session->query.clear();
313
310
 
314
311
  session->set_proc_info(NULL);
315
312
  free_root(session->mem_root,MYF(memory::KEEP_PREALLOC));
463
460
  /* list of all tables in query */
464
461
  TableList *all_tables;
465
462
  /* A peek into the query string */
466
 
  size_t proc_info_len= session->query_length > PROCESS_LIST_WIDTH ?
467
 
                        PROCESS_LIST_WIDTH : session->query_length;
 
463
  size_t proc_info_len= session->query.length() > PROCESS_LIST_WIDTH ?
 
464
                        PROCESS_LIST_WIDTH : session->query.length();
468
465
 
469
 
  memcpy(session->process_list_info, session->query, proc_info_len);
 
466
  memcpy(session->process_list_info, session->query.c_str(), proc_info_len);
470
467
  session->process_list_info[proc_info_len]= '\0';
471
468
 
472
469
  /*
742
739
  @param       session     Current thread
743
740
  @param       inBuf   Begining of the query text
744
741
  @param       length  Length of the query text
745
 
  @param[out]  found_semicolon For multi queries, position of the character of
746
 
                               the next query in the query text.
747
742
*/
748
743
 
749
 
void mysql_parse(Session *session, const char *inBuf, uint32_t length,
750
 
                 const char ** found_semicolon)
 
744
void mysql_parse(Session *session, const char *inBuf, uint32_t length)
751
745
{
752
 
  /*
753
 
    Warning.
754
 
    The purpose of query_cache_send_result_to_client() is to lookup the
755
 
    query in the query cache first, to avoid parsing and executing it.
756
 
    So, the natural implementation would be to:
757
 
    - first, call query_cache_send_result_to_client,
758
 
    - second, if caching failed, initialise the lexical and syntactic parser.
759
 
    The problem is that the query cache depends on a clean initialization
760
 
    of (among others) lex->safe_to_cache_query and session->server_status,
761
 
    which are reset respectively in
762
 
    - lex_start()
763
 
    - mysql_reset_session_for_next_command()
764
 
    So, initializing the lexical analyser *before* using the query cache
765
 
    is required for the cache to work properly.
766
 
    FIXME: cleanup the dependencies in the code to simplify this.
767
 
  */
768
746
  lex_start(session);
769
747
  session->reset_for_next_command();
770
748
 
 
749
  LEX *lex= session->lex;
 
750
 
 
751
  Lex_input_stream lip(session, inBuf, length);
 
752
 
 
753
  bool err= parse_sql(session, &lip);
 
754
 
 
755
  if (!err)
771
756
  {
772
 
    LEX *lex= session->lex;
773
 
 
774
 
    Lex_input_stream lip(session, inBuf, length);
775
 
 
776
 
    bool err= parse_sql(session, &lip);
777
 
    *found_semicolon= lip.found_semicolon;
778
 
 
779
 
    if (!err)
780
757
    {
 
758
      if (! session->is_error())
781
759
      {
782
 
        if (! session->is_error())
783
 
        {
784
 
          /*
785
 
            Binlog logs a string starting from session->query and having length
786
 
            session->query_length; so we set session->query_length correctly (to not
787
 
            log several statements in one event, when we executed only first).
788
 
            We set it to not see the ';' (otherwise it would get into binlog
789
 
            and Query_log_event::print() would give ';;' output).
790
 
            This also helps display only the current query in SHOW
791
 
            PROCESSLIST.
792
 
            Note that we don't need LOCK_thread_count to modify query_length.
793
 
          */
794
 
          if (*found_semicolon &&
795
 
              (session->query_length= (ulong)(*found_semicolon - session->query)))
796
 
            session->query_length--;
797
 
          DRIZZLE_QUERY_EXEC_START(session->query,
798
 
                                   session->thread_id,
799
 
                                   const_cast<const char *>(session->db.empty() ? "" : session->db.c_str()));
800
 
          /* Actually execute the query */
801
 
          mysql_execute_command(session);
802
 
          DRIZZLE_QUERY_EXEC_DONE(0);
803
 
        }
 
760
        DRIZZLE_QUERY_EXEC_START(session->query.c_str(),
 
761
                                 session->thread_id,
 
762
                                 const_cast<const char *>(session->db.empty() ? "" : session->db.c_str()));
 
763
        /* Actually execute the query */
 
764
        mysql_execute_command(session);
 
765
        DRIZZLE_QUERY_EXEC_DONE(0);
804
766
      }
805
767
    }
806
 
    else
807
 
    {
808
 
      assert(session->is_error());
809
 
    }
810
 
    lex->unit.cleanup();
811
 
    session->set_proc_info("freeing items");
812
 
    session->end_statement();
813
 
    session->cleanup_after_query();
814
 
  }
 
768
  }
 
769
  else
 
770
  {
 
771
    assert(session->is_error());
 
772
  }
 
773
 
 
774
  lex->unit.cleanup();
 
775
  session->set_proc_info("freeing items");
 
776
  session->end_statement();
 
777
  session->cleanup_after_query();
815
778
 
816
779
  return;
817
780
}
1818
1781
{
1819
1782
  assert(session->m_lip == NULL);
1820
1783
 
1821
 
  DRIZZLE_QUERY_PARSE_START(session->query);
 
1784
  DRIZZLE_QUERY_PARSE_START(session->query.c_str());
1822
1785
 
1823
1786
  /* Set Lex_input_stream. */
1824
1787