/* ================================================================= Copyright (C) 2012 2013 BizStation Corp All rights reserved. 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 "client.h" #include "sqlBuilder.h" #include "stringConverter.h" using namespace bzs::db::protocol::tdap::client; bzs::netsvc::client::connections* m_cons = NULL; namespace bzs { namespace db { namespace protocol { namespace tdap { namespace client { #ifdef USETLS tls_key g_tlsiID; #else __THREAD client* __THREAD_BCB g_client = NULL; #endif int client::getServerCharsetIndex() { bzs::netsvc::client::connection* c = con(); if (!c) return -1; int v = c->charsetServer(); if (v != -1) return v; request req = m_req; req.paramMask = P_MASK_POSBLK | P_MASK_DATA | P_MASK_DATALEN; trdVersiton ver; memset(&ver, 0, sizeof(trdVersiton)); ver.cherserServer[0] = 0x00; ver.clMajor = (ushort_td)atoi(C_INTERFACE_VER_MAJOR); ver.clMinor = (ushort_td)atoi(C_INTERFACE_VER_MINOR); ver.clRelease = (ushort_td)atoi(C_INTERFACE_VER_RELEASE); uint_td len = sizeof(trdVersiton); req.op = TD_GETSERVER_CHARSET; req.data = &ver; req.datalen = &len; mutex::scoped_lock lck(m_mutex); char* p = con()->sendBuffer(m_req.sendLenEstimate()); unsigned int size = req.serialize(p); p = con()->asyncWriteRead(size); req.parse(p, false); if (req.result == 0) { if (!checkVersion(ver)) return -1; c->setCharsetServer(mysql::charsetIndex(ver.cherserServer)); return c->charsetServer(); } return -1; } void client::addSecondCharsetData(unsigned int destCodePage, std::string& src) { stringConverter cv(destCodePage, CP_UTF8); int osize = (int)src.size() * 3; char* srvchar = new char[osize]; size_t len = cv.convert(srvchar, osize, src.c_str(), src.size()); srvchar[len] = 0x00; src += std::string("\t") + srvchar; delete[] srvchar; } bool client::buildDualChasetKeybuf() { int charsetIndexServer = getServerCharsetIndex(); if (charsetIndexServer == -1) return false; // remove auth info { _TCHAR tmp[MAX_KEYLEN+128]={0}; m_serverCharData = stripAuth((const char*)m_req.keybuf, tmp, MAX_KEYLEN); if (CHARSET_UTF8 != charsetIndexServer) addSecondCharsetData(mysql::codePage(charsetIndexServer), m_serverCharData); else m_serverCharData += std::string("\t") + tmp; } //Add Auth infomation if (m_cryptPwd) m_serverCharData += std::string("\t") + std::string(m_cryptPwd, strlen(m_cryptPwd + 20) + MYSQL_SCRAMBLE_LENGTH); m_req.keybuf = (void_td*)m_serverCharData.c_str(); m_req.keylen = (keylen_td)m_serverCharData.size(); return true; } } // namespace client } // namespace tdap } // namespace protocol } // namespace db } // namespace bzs