libmysqld.c 6.68 KB
Newer Older
unknown's avatar
unknown committed
1 2 3 4 5 6 7 8
/* Copyright (C) 2000 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,
9
   but WITHOUT ANY WARRANTY; without even the implied warranty of
unknown's avatar
unknown committed
10 11 12 13 14 15
   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 */
unknown's avatar
unknown committed
16

unknown's avatar
unknown committed
17
#include "embedded_priv.h"
18 19 20 21 22 23 24 25 26
#include <my_sys.h>
#include <mysys_err.h>
#include <m_string.h>
#include <m_ctype.h>
#include "errmsg.h"
#include <violite.h>
#include <sys/stat.h>
#include <signal.h>
#include <time.h>
unknown's avatar
SCRUM  
unknown committed
27
#include "client_settings.h"
28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76
#ifdef	 HAVE_PWD_H
#include <pwd.h>
#endif
#if !defined(MSDOS) && !defined(__WIN__)
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <netdb.h>
#ifdef HAVE_SELECT_H
#  include <select.h>
#endif
#ifdef HAVE_SYS_SELECT_H
#include <sys/select.h>
#endif
#endif
#ifdef HAVE_SYS_UN_H
#  include <sys/un.h>
#endif
#ifndef INADDR_NONE
#define INADDR_NONE	-1
#endif

#if defined(MSDOS) || defined(__WIN__)
#define ERRNO WSAGetLastError()
#define perror(A)
#else
#include <errno.h>
#define ERRNO errno
#define SOCKET_ERROR -1
#define closesocket(A) close(A)
#endif

#ifdef HAVE_GETPWUID
struct passwd *getpwuid(uid_t);
char* getlogin(void);
#endif

#ifdef __WIN__
static my_bool is_NT(void)
{
  char *os=getenv("OS");
  return (os && !strcmp(os, "Windows_NT")) ? 1 : 0;
}
#endif

/**************************************************************************
** Shut down connection
**************************************************************************/

unknown's avatar
SCRUM  
unknown committed
77
static void end_server(MYSQL *mysql)
78 79 80 81 82 83
{
  DBUG_ENTER("end_server");
  free_old_query(mysql);
  DBUG_VOID_RETURN;
}

84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107
static inline int mysql_init_charset(MYSQL *mysql)
{
  char charset_name_buff[16], *charset_name;

  if ((charset_name=mysql->options.charset_name))
  {
    const char *save=charsets_dir;
    if (mysql->options.charset_dir)
      charsets_dir=mysql->options.charset_dir;
    mysql->charset=get_charset_by_name(mysql->options.charset_name,
                                       MYF(MY_WME));
    charsets_dir=save;
  }
  else if (mysql->server_language)
  {
    charset_name=charset_name_buff;
    sprintf(charset_name,"%d",mysql->server_language);	/* In case of errors */
    mysql->charset=get_charset((uint8) mysql->server_language, MYF(MY_WME));
  }
  else
    mysql->charset=default_charset_info;

  if (!mysql->charset)
  {
108 109
    mysql->net.last_errno=CR_CANT_READ_CHARSET;
    strmov(mysql->net.sqlstate, "HY0000");
110
    if (mysql->options.charset_dir)
111
      sprintf(mysql->net.last_error,ER(mysql->net.last_errno),
112 113 114 115 116 117
              charset_name ? charset_name : "unknown",
              mysql->options.charset_dir);
    else
    {
      char cs_dir_name[FN_REFLEN];
      get_charsets_dir(cs_dir_name);
118
      sprintf(mysql->net.last_error,ER(mysql->net.last_errno),
119 120 121
              charset_name ? charset_name : "unknown",
              cs_dir_name);
    }
122
    return mysql->net.last_errno;
123 124 125 126
  }
  return 0;
}

unknown's avatar
unknown committed
127 128
int check_embedded_connection(MYSQL *mysql);

129 130
MYSQL * STDCALL
mysql_real_connect(MYSQL *mysql,const char *host, const char *user,
unknown's avatar
SCRUM  
unknown committed
131
		   const char *passwd, const char *db,
unknown's avatar
unknown committed
132
		   uint port, const char *unix_socket,ulong client_flag)
133
{
unknown's avatar
unknown committed
134 135 136 137
  char *db_name;
#ifndef NO_EMBEDDED_ACCESS_CHECKS
  char name_buff[USERNAME_LENGTH];
#endif
138 139 140 141 142 143
  DBUG_ENTER("mysql_real_connect");
  DBUG_PRINT("enter",("host: %s  db: %s  user: %s",
		      host ? host : "(Null)",
		      db ? db : "(Null)",
		      user ? user : "(Null)"));

unknown's avatar
unknown committed
144
#if defined(EMBEDDED_LIBRARY) || !defined(DBUG_OFF)
unknown's avatar
unknown committed
145 146 147 148 149 150
  if (!server_inited)
  {
    mysql->net.last_errno=CR_MYSQL_SERVER_INIT_MISSED;
    strmov(mysql->net.last_error,ER(mysql->net.last_errno));
    goto error;
  }
unknown's avatar
unknown committed
151
#endif
unknown's avatar
unknown committed
152

unknown's avatar
unknown committed
153 154 155
  if (mysql->options.methods_to_use == MYSQL_OPT_USE_REMOTE_CONNECTION ||
      (mysql->options.methods_to_use == MYSQL_OPT_GUESS_CONNECTION &&
       host && strcmp(host,LOCAL_HOST)))
unknown's avatar
SCRUM  
unknown committed
156 157 158
    cli_mysql_real_connect(mysql, host, user, 
			   passwd, db, port, unix_socket, client_flag);

unknown's avatar
SCRUM  
unknown committed
159 160
  mysql->methods= &embedded_methods;

161 162 163 164 165 166 167 168 169 170 171 172 173 174
  /* use default options */
  if (mysql->options.my_cnf_file || mysql->options.my_cnf_group)
  {
    mysql_read_default_options(&mysql->options,
			       (mysql->options.my_cnf_file ?
				mysql->options.my_cnf_file : "my"),
			       mysql->options.my_cnf_group);
    my_free(mysql->options.my_cnf_file,MYF(MY_ALLOW_ZERO_PTR));
    my_free(mysql->options.my_cnf_group,MYF(MY_ALLOW_ZERO_PTR));
    mysql->options.my_cnf_file=mysql->options.my_cnf_group=0;
  }

  if (!db || !db[0])
    db=mysql->options.db;
175

unknown's avatar
unknown committed
176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198
#ifndef NO_EMBEDDED_ACCESS_CHECKS
  if (!user || !user[0])
    user=mysql->options.user;

  if (!passwd)
  {
    passwd=mysql->options.password;
#if !defined(DONT_USE_MYSQL_PWD)
    if (!passwd)
      passwd=getenv("MYSQL_PWD");		/* get it from environment */
#endif
  }
  if (!user || !user[0])
  {
    read_user_name(name_buff);
    if (!name_buff[0])
      user= name_buff;
  }

  mysql->user=my_strdup(user,MYF(0));
  mysql->passwd= passwd ? my_strdup(passwd,MYF(0)) : NULL;
#endif /*!NO_EMBEDDED_ACCESS_CHECKS*/

unknown's avatar
unknown committed
199 200
  port=0;
  unix_socket=0;
201 202
  db_name = db ? my_strdup(db,MYF(MY_WME)) : NULL;

203
  mysql->thd= create_embedded_thd(client_flag, db_name);
204

205
  init_embedded_mysql(mysql, client_flag, db_name);
206

unknown's avatar
unknown committed
207 208 209 210 211
#ifndef NO_EMBEDDED_ACCESS_CHECKS
  if (check_embedded_connection(mysql))
    goto error;
#endif

212
  if (mysql_init_charset(mysql))
213 214 215 216
    goto error;

  /* Send client information for access check */
  client_flag|=CLIENT_CAPABILITIES;
unknown's avatar
unknown committed
217
  client_flag&= ~CLIENT_COMPRESS;
218 219
  if (db)
    client_flag|=CLIENT_CONNECT_WITH_DB;
unknown's avatar
unknown committed
220
  mysql->server_status= SERVER_STATUS_AUTOCOMMIT;
unknown's avatar
unknown committed
221

unknown's avatar
unknown committed
222
  if (mysql->options.init_commands)
223
  {
unknown's avatar
unknown committed
224 225 226 227 228 229 230 231 232 233 234
    DYNAMIC_ARRAY *init_commands= mysql->options.init_commands;
    char **ptr= (char**)init_commands->buffer;
    char **end= ptr + init_commands->elements;

    for (; ptr<end; ptr++)
    {
      MYSQL_RES *res;
      if (mysql_query(mysql,*ptr))
	goto error;
      if (mysql->fields)
      {
unknown's avatar
unknown committed
235
	if (!(res= (*mysql->methods->use_result)(mysql)))
unknown's avatar
unknown committed
236 237 238 239
	  goto error;
	mysql_free_result(res);
      }
    }
240 241 242 243 244 245
  }

  DBUG_PRINT("exit",("Mysql handler: %lx",mysql));
  DBUG_RETURN(mysql);

error:
unknown's avatar
unknown committed
246 247
  DBUG_PRINT("error",("message: %u (%s)", mysql->net.last_errno,
		      mysql->net.last_error));
248 249 250 251 252 253 254 255 256 257 258
  {
    /* Free alloced memory */
    my_bool free_me=mysql->free_me;
    end_server(mysql);
    mysql->free_me=0;
    mysql_close(mysql);
    mysql->free_me=free_me;
  }
  DBUG_RETURN(0);
}