diff options
167 files changed, 4023 insertions, 982 deletions
diff --git a/.bzrignore b/.bzrignore index 7e6c6985e23..ecaa4b60c51 100644 --- a/.bzrignore +++ b/.bzrignore @@ -1051,6 +1051,7 @@ ndbcluster-1186/ndb_3.pid ndbcluster-1186/ndb_3_cluster.log ndbcluster-1186/ndb_3_out.log ndbcluster-1186/ndbcluster.pid +netware/libmysql.imp pack_isam/*.ds? perror/*.ds? perror/*.vcproj diff --git a/BitKeeper/etc/collapsed b/BitKeeper/etc/collapsed index bbf04965038..79836bb030e 100644 --- a/BitKeeper/etc/collapsed +++ b/BitKeeper/etc/collapsed @@ -5,3 +5,5 @@ 45001f7c3b2hhCXDKfUvzkX9TNe6VA 45002051rHJfMEXAIMiAZV0clxvKSA 4513d8e4Af4dQWuk13sArwofRgFDQw +4519a6c5BVUxEHTf5iJnjZkixMBs8g +451ab499rgdjXyOnUDqHu-wBDoS-OQ diff --git a/CMakeLists.txt b/CMakeLists.txt index fd780ec6a13..8058f615f7c 100755 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -29,8 +29,6 @@ IF (WITH_MYISAMMRG_STORAGE_ENGINE) ENDIF (WITH_MYISAMMRG_STORAGE_ENGINE) IF(WITH_INNOBASE_STORAGE_ENGINE) - CONFIGURE_FILE(${CMAKE_SOURCE_DIR}/innobase/ib_config.h.in - ${CMAKE_SOURCE_DIR}/innobase/ib_config.h @ONLY) ADD_DEFINITIONS(-D HAVE_INNOBASE_DB) ADD_DEFINITIONS(-D WITH_INNOBASE_STORAGE_ENGINE) SET (mysql_plugin_defs "${mysql_plugin_defs},builtin_innobase_plugin") @@ -123,8 +121,12 @@ ADD_SUBDIRECTORY(heap) ADD_SUBDIRECTORY(myisam) ADD_SUBDIRECTORY(myisammrg) ADD_SUBDIRECTORY(client) +IF(WITH_BERKELEY_STORAGE_ENGINE) ADD_SUBDIRECTORY(bdb) +ENDIF(WITH_BERKELEY_STORAGE_ENGINE) +IF(WITH_INNOBASE_STORAGE_ENGINE) ADD_SUBDIRECTORY(innobase) +ENDIF(WITH_INNOBASE_STORAGE_ENGINE) ADD_SUBDIRECTORY(sql) ADD_SUBDIRECTORY(sql/examples) ADD_SUBDIRECTORY(server-tools/instance-manager) diff --git a/client/mysql.cc b/client/mysql.cc index 5e09c309917..1d7abbbc38a 100644 --- a/client/mysql.cc +++ b/client/mysql.cc @@ -49,6 +49,9 @@ const char *VER= "14.12"; /* Don't try to make a nice table if the data is too big */ #define MAX_COLUMN_LENGTH 1024 +/* Buffer to hold 'version' and 'version_comment' */ +#define MAX_SERVER_VERSION_LENGTH 128 + gptr sql_alloc(unsigned size); // Don't use mysqld alloc for these void sql_element_free(void *ptr); #include "sql_string.h" @@ -208,6 +211,7 @@ static int com_nopager(String *str, char*), com_pager(String *str, char*), static int read_and_execute(bool interactive); static int sql_connect(char *host,char *database,char *user,char *password, uint silent); +static const char *server_version_string(MYSQL *mysql); static int put_info(const char *str,INFO_TYPE info,uint error=0, const char *sql_state=0); static int put_error(MYSQL *mysql); @@ -432,8 +436,8 @@ int main(int argc,char *argv[]) put_info("Welcome to the MySQL monitor. Commands end with ; or \\g.", INFO_INFO); sprintf((char*) glob_buffer.ptr(), - "Your MySQL connection id is %lu to server version: %s\n", - mysql_thread_id(&mysql),mysql_get_server_info(&mysql)); + "Your MySQL connection id is %lu\nServer version: %s\n", + mysql_thread_id(&mysql), server_version_string(&mysql)); put_info((char*) glob_buffer.ptr(),INFO_INFO); #ifdef HAVE_READLINE @@ -2509,9 +2513,14 @@ print_table_data_xml(MYSQL_RES *result) { tee_fprintf(PAGER, "\t<field name=\""); xmlencode_print(fields[i].name, (uint) strlen(fields[i].name)); - tee_fprintf(PAGER, "\">"); - xmlencode_print(cur[i], lengths[i]); - tee_fprintf(PAGER, "</field>\n"); + if (cur[i]) + { + tee_fprintf(PAGER, "\">"); + xmlencode_print(cur[i], lengths[i]); + tee_fprintf(PAGER, "</field>\n"); + } + else + tee_fprintf(PAGER, "\" xsi:nil=\"true\" />\n"); } (void) tee_fputs(" </row>\n", PAGER); } @@ -2910,7 +2919,7 @@ com_connect(String *buffer, char *line) bzero(buff, sizeof(buff)); if (buffer) { - strmake(buff, line, sizeof(buff)); + strmake(buff, line, sizeof(buff) - 1); tmp= get_arg(buff, 0); if (tmp && *tmp) { @@ -3025,7 +3034,7 @@ com_use(String *buffer __attribute__((unused)), char *line) int select_db; bzero(buff, sizeof(buff)); - strmov(buff, line); + strmake(buff, line, sizeof(buff) - 1); tmp= get_arg(buff, 0); if (!tmp || !*tmp) { @@ -3335,16 +3344,13 @@ com_status(String *buffer __attribute__((unused)), tee_fprintf(stdout, "Using outfile:\t\t'%s'\n", opt_outfile ? outfile : ""); #endif tee_fprintf(stdout, "Using delimiter:\t%s\n", delimiter); - tee_fprintf(stdout, "Server version:\t\t%s\n", mysql_get_server_info(&mysql)); + tee_fprintf(stdout, "Server version:\t\t%s\n", server_version_string(&mysql)); tee_fprintf(stdout, "Protocol version:\t%d\n", mysql_get_proto_info(&mysql)); tee_fprintf(stdout, "Connection:\t\t%s\n", mysql_get_host_info(&mysql)); if ((id= mysql_insert_id(&mysql))) tee_fprintf(stdout, "Insert id:\t\t%s\n", llstr(id, buff)); - /* - Don't remove "limit 1", - it is protection againts SQL_SELECT_LIMIT=0 - */ + /* "limit 1" is protection against SQL_SELECT_LIMIT=0 */ if (!mysql_query(&mysql,"select @@character_set_client, @@character_set_connection, @@character_set_server, @@character_set_database limit 1") && (result=mysql_use_result(&mysql))) { @@ -3409,6 +3415,39 @@ select_limit, max_join_size); return 0; } +static const char * +server_version_string(MYSQL *mysql) +{ + static char buf[MAX_SERVER_VERSION_LENGTH] = ""; + + /* Only one thread calls this, so no synchronization is needed */ + if (buf[0] == '\0') + { + char *bufp = buf; + MYSQL_RES *result; + MYSQL_ROW cur; + + bufp = strnmov(buf, mysql_get_server_info(mysql), sizeof buf); + + /* "limit 1" is protection against SQL_SELECT_LIMIT=0 */ + if (!mysql_query(mysql, "select @@version_comment limit 1") && + (result = mysql_use_result(mysql))) + { + MYSQL_ROW cur = mysql_fetch_row(result); + if (cur && cur[0]) + { + bufp = strxnmov(bufp, sizeof buf - (bufp - buf), " ", cur[0], NullS); + } + mysql_free_result(result); + } + + /* str*nmov doesn't guarantee NUL-termination */ + if (bufp == buf + sizeof buf) + buf[sizeof buf - 1] = '\0'; + } + + return buf; +} static int put_info(const char *str,INFO_TYPE info_type, uint error, const char *sqlstate) @@ -3536,14 +3575,14 @@ void tee_puts(const char *s, FILE *file) { NETWARE_YIELD; fputs(s, file); - fputs("\n", file); + fputc('\n', file); #ifdef OS2 - fflush( file); + fflush(file); #endif if (opt_outfile) { fputs(s, OUTFILE); - fputs("\n", OUTFILE); + fputc('\n', OUTFILE); } } diff --git a/client/mysqltest.c b/client/mysqltest.c index 0f0abe682b5..c0319eee259 100644 --- a/client/mysqltest.c +++ b/client/mysqltest.c @@ -1608,8 +1608,12 @@ int do_save_master_pos() int do_let(struct st_query *query) { + int ret; char *p= query->first_argument; - char *var_name, *var_name_end, *var_val_start; + char *var_name, *var_name_end; + DYNAMIC_STRING let_rhs_expr; + + init_dynamic_string(&let_rhs_expr, "", 512, 2048); /* Find <var_name> */ if (!*p) @@ -1628,10 +1632,16 @@ int do_let(struct st_query *query) /* Find start of <var_val> */ while (*p && my_isspace(charset_info,*p)) p++; - var_val_start= p; + + do_eval(&let_rhs_expr, p, FALSE); + query->last_argument= query->end; /* Assign var_val to var_name */ - return var_set(var_name, var_name_end, var_val_start, query->end); + ret= var_set(var_name, var_name_end, let_rhs_expr.str, + (let_rhs_expr.str + let_rhs_expr.length)); + dynstr_free(&let_rhs_expr); + + return(ret); } diff --git a/config/ac-macros/yassl.m4 b/config/ac-macros/yassl.m4 index 2dc231c1f5a..967dcbf764a 100644 --- a/config/ac-macros/yassl.m4 +++ b/config/ac-macros/yassl.m4 @@ -18,7 +18,8 @@ AC_DEFUN([MYSQL_CHECK_YASSL], [ fi AC_MSG_RESULT([using bundled yaSSL]) yassl_dir="extra/yassl" - yassl_libs="-L\$(top_srcdir)/extra/yassl/src -lyassl -L\$(top_srcdir)/extra/yassl/taocrypt/src -ltaocrypt" + yassl_libs="\$(top_builddir)/extra/yassl/src/libyassl.la \ + \$(top_builddir)/extra/yassl/taocrypt/src/libtaocrypt.la" AC_DEFINE([HAVE_OPENSSL], [1], [Defined by configure. Using yaSSL for OpenSSL emulation.]) AC_DEFINE([HAVE_YASSL], [1], [Defined by configure. Using yaSSL for OpenSSL emulation.]) # System specific checks diff --git a/extra/Makefile.am b/extra/Makefile.am index 0de513ba15a..63d2b4055f7 100644 --- a/extra/Makefile.am +++ b/extra/Makefile.am @@ -22,14 +22,18 @@ BUILT_SOURCES= $(top_builddir)/include/mysqld_error.h \ $(top_builddir)/include/sql_state.h \ $(top_builddir)/include/mysqld_ername.h pkginclude_HEADERS= $(BUILT_SOURCES) -CLEANFILES = $(BUILT_SOURCES) +DISTCLEANFILES = $(BUILT_SOURCES) # We never use SUBDIRS here, but needed for automake 1.6.3 # to generate code to handle DIST_SUBDIRS SUBDIRS= DIST_SUBDIRS= yassl -# This will build mysqld_error.h and sql_state.h -$(top_builddir)/include/mysqld_error.h: comp_err$(EXEEXT) +# This will build mysqld_error.h, mysqld_ername.h and sql_state.h +# NOTE Built files should depend on their sources to avoid +# the built files being rebuilt in source dist +$(top_builddir)/include/mysqld_error.h: comp_err.c \ + $(top_srcdir)/sql/share/errmsg.txt + $(MAKE) $(AM_MAKEFLAGS) comp_err$(EXEEXT) $(top_builddir)/extra/comp_err$(EXEEXT) \ --charset=$(top_srcdir)/sql/share/charsets \ --out-dir=$(top_builddir)/sql/share/ \ diff --git a/extra/yassl/CMakeLists.txt b/extra/yassl/CMakeLists.txt index e5429876072..09bd2b046da 100755 --- a/extra/yassl/CMakeLists.txt +++ b/extra/yassl/CMakeLists.txt @@ -1,6 +1,6 @@ ADD_DEFINITIONS("-DWIN32 -D_LIB -DYASSL_PREFIX") -INCLUDE_DIRECTORIES(include taocrypt/include mySTL) +INCLUDE_DIRECTORIES(include taocrypt/include taocrypt/mySTL) ADD_LIBRARY(yassl src/buffer.cpp src/cert_wrapper.cpp src/crypto_wrapper.cpp src/handshake.cpp src/lock.cpp src/log.cpp src/socket_wrapper.cpp src/ssl.cpp src/timer.cpp src/yassl_error.cpp src/yassl_imp.cpp src/yassl_int.cpp) diff --git a/extra/yassl/FLOSS-EXCEPTIONS b/extra/yassl/FLOSS-EXCEPTIONS index 344083b0114..47f86ff65f2 100644 --- a/extra/yassl/FLOSS-EXCEPTIONS +++ b/extra/yassl/FLOSS-EXCEPTIONS @@ -1,7 +1,7 @@ yaSSL FLOSS License Exception **************************************** -Version 0.1, 26 June 2006 +Version 0.2, 31 August 2006 The Sawtooth Consulting Ltd. Exception for Free/Libre and Open Source Software-only Applications Using yaSSL Libraries (the "FLOSS Exception"). @@ -81,6 +81,7 @@ the GPL: Python license (CNRI Python License) - Python Software Foundation License 2.1.1 Sleepycat License "1999" + University of Illinois/NCSA Open Source License - W3C License "2001" X11 License "2001" Zlib/libpng License - diff --git a/extra/yassl/Makefile.am b/extra/yassl/Makefile.am index 12a7da1085b..b7657dc28f9 100644 --- a/extra/yassl/Makefile.am +++ b/extra/yassl/Makefile.am @@ -1,2 +1,2 @@ SUBDIRS = taocrypt src testsuite -EXTRA_DIST = yassl.dsp yassl.dsw $(wildcard mySTL/*.hpp) CMakeLists.txt +EXTRA_DIST = yassl.dsp yassl.dsw CMakeLists.txt diff --git a/extra/yassl/README b/extra/yassl/README index 25d4d94c306..2af4e98fe4c 100644 --- a/extra/yassl/README +++ b/extra/yassl/README @@ -1,4 +1,15 @@ -yaSSL Release notes, version 1.3.7 (06/26/06) +yaSSL Release notes, version 1.4.0 (08/13/06) + + + This release of yaSSL contains bug fixes, portability enhancements, + nonblocking connect and accept, better OpenSSL error mapping, and + certificate caching for session resumption. + +See normal build instructions below under 1.0.6. +See libcurl build instructions below under 1.3.0. + + +********************yaSSL Release notes, version 1.3.7 (06/26/06) This release of yaSSL contains bug fixes, portability enhancements, diff --git a/extra/yassl/examples/client/client.cpp b/extra/yassl/examples/client/client.cpp index 94bf753210b..d655011deb6 100644 --- a/extra/yassl/examples/client/client.cpp +++ b/extra/yassl/examples/client/client.cpp @@ -27,7 +27,13 @@ void client_test(void* args) SSL_set_fd(ssl, sockfd); - if (SSL_connect(ssl) != SSL_SUCCESS) err_sys("SSL_connect failed"); + if (SSL_connect(ssl) != SSL_SUCCESS) + { + SSL_CTX_free(ctx); + SSL_free(ssl); + tcp_close(sockfd); + err_sys("SSL_connect failed"); + } showPeer(ssl); const char* cipher = 0; @@ -39,11 +45,16 @@ void client_test(void* args) strncat(list, cipher, strlen(cipher) + 1); } printf("%s\n", list); - printf("Using Cipher Suite %s\n", SSL_get_cipher(ssl)); + printf("Using Cipher Suite: %s\n", SSL_get_cipher(ssl)); char msg[] = "hello yassl!"; if (SSL_write(ssl, msg, sizeof(msg)) != sizeof(msg)) + { + SSL_CTX_free(ctx); + SSL_free(ssl); + tcp_close(sockfd); err_sys("SSL_write failed"); + } char reply[1024]; reply[SSL_read(ssl, reply, sizeof(reply))] = 0; @@ -56,22 +67,36 @@ void client_test(void* args) SSL_shutdown(ssl); SSL_free(ssl); + tcp_close(sockfd); #ifdef TEST_RESUME tcp_connect(sockfd); SSL_set_fd(sslResume, sockfd); SSL_set_session(sslResume, session); - if (SSL_connect(sslResume) != SSL_SUCCESS) err_sys("SSL resume failed"); + if (SSL_connect(sslResume) != SSL_SUCCESS) + { + SSL_CTX_free(ctx); + SSL_free(ssl); + tcp_close(sockfd); + err_sys("SSL resume failed"); + } + showPeer(sslResume); if (SSL_write(sslResume, msg, sizeof(msg)) != sizeof(msg)) + { + SSL_CTX_free(ctx); + SSL_free(ssl); + tcp_close(sockfd); err_sys("SSL_write failed"); + } reply[SSL_read(sslResume, reply, sizeof(reply))] = 0; printf("Server response: %s\n", reply); SSL_shutdown(sslResume); SSL_free(sslResume); + tcp_close(sockfd); #endif // TEST_RESUME SSL_CTX_free(ctx); diff --git a/extra/yassl/examples/echoclient/echoclient.cpp b/extra/yassl/examples/echoclient/echoclient.cpp index fd3f7dd48a3..983254bf8a7 100644 --- a/extra/yassl/examples/echoclient/echoclient.cpp +++ b/extra/yassl/examples/echoclient/echoclient.cpp @@ -41,7 +41,14 @@ void echoclient_test(void* args) SSL* ssl = SSL_new(ctx); SSL_set_fd(ssl, sockfd); - if (SSL_connect(ssl) != SSL_SUCCESS) err_sys("SSL_connect failed"); + + if (SSL_connect(ssl) != SSL_SUCCESS) + { + SSL_CTX_free(ctx); + SSL_free(ssl); + tcp_close(sockfd); + err_sys("SSL_connect failed"); + } char send[1024]; char reply[1024]; @@ -50,7 +57,12 @@ void echoclient_test(void* args) int sendSz = strlen(send) + 1; if (SSL_write(ssl, send, sendSz) != sendSz) + { + SSL_CTX_free(ctx); + SSL_free(ssl); + tcp_close(sockfd); err_sys("SSL_write failed"); + } if (strncmp(send, "quit", 4) == 0) { fputs("sending server shutdown command: quit!\n", fout); @@ -63,6 +75,7 @@ void echoclient_test(void* args) SSL_CTX_free(ctx); SSL_free(ssl); + tcp_close(sockfd); fflush(fout); if (inCreated) fclose(fin); diff --git a/extra/yassl/examples/echoserver/echoserver.cpp b/extra/yassl/examples/echoserver/echoserver.cpp index 8e23ead20ab..cd31fedddd8 100644 --- a/extra/yassl/examples/echoserver/echoserver.cpp +++ b/extra/yassl/examples/echoserver/echoserver.cpp @@ -23,6 +23,18 @@ #endif // NO_MAIN_DRIVER + +void EchoError(SSL_CTX* ctx, SSL* ssl, SOCKET_T& s1, SOCKET_T& s2, + const char* msg) +{ + SSL_CTX_free(ctx); + SSL_free(ssl); + tcp_close(s1); + tcp_close(s2); + err_sys(msg); +} + + THREAD_RETURN YASSL_API echoserver_test(void* args) { #ifdef _WIN32 @@ -65,13 +77,18 @@ THREAD_RETURN YASSL_API echoserver_test(void* args) while (!shutdown) { sockaddr_in client; socklen_t client_len = sizeof(client); - int clientfd = accept(sockfd, (sockaddr*)&client, + SOCKET_T clientfd = accept(sockfd, (sockaddr*)&client, (ACCEPT_THIRD_T)&client_len); - if (clientfd == -1) err_sys("tcp accept failed"); + if (clientfd == -1) { + SSL_CTX_free(ctx); + tcp_close(sockfd); + err_sys("tcp accept failed"); + } SSL* ssl = SSL_new(ctx); SSL_set_fd(ssl, clientfd); - if (SSL_accept(ssl) != SSL_SUCCESS) err_sys("SSL_accept failed"); + if (SSL_accept(ssl) != SSL_SUCCESS) + EchoError(ctx, ssl, sockfd, clientfd, "SSL_accept failed"); char command[1024]; int echoSz(0); @@ -100,7 +117,8 @@ THREAD_RETURN YASSL_API echoserver_test(void* args) echoSz += sizeof(footer); if (SSL_write(ssl, command, echoSz) != echoSz) - err_sys("SSL_write failed"); + EchoError(ctx, ssl, sockfd, clientfd, "SSL_write failed"); + break; } command[echoSz] = 0; @@ -110,16 +128,13 @@ THREAD_RETURN YASSL_API echoserver_test(void* args) #endif if (SSL_write(ssl, command, echoSz) != echoSz) - err_sys("SSL_write failed"); + EchoError(ctx, ssl, sockfd, clientfd, "SSL_write failed"); } SSL_free(ssl); + tcp_close(clientfd); } -#ifdef _WIN32 - closesocket(sockfd); -#else - close(sockfd); -#endif + tcp_close(sockfd); DH_free(dh); SSL_CTX_free(ctx); diff --git a/extra/yassl/examples/server/server.cpp b/extra/yassl/examples/server/server.cpp index 73cff19e371..d0bf70cd634 100644 --- a/extra/yassl/examples/server/server.cpp +++ b/extra/yassl/examples/server/server.cpp @@ -4,6 +4,15 @@ #include "../../testsuite/test.hpp" +void ServerError(SSL_CTX* ctx, SSL* ssl, SOCKET_T& sockfd, const char* msg) +{ + SSL_CTX_free(ctx); + SSL_free(ssl); + tcp_close(sockfd); + err_sys(msg); +} + + THREAD_RETURN YASSL_API server_test(void* args) { #ifdef _WIN32 @@ -12,18 +21,14 @@ THREAD_RETURN YASSL_API server_test(void* args) #endif SOCKET_T sockfd = 0; - int clientfd = 0; + SOCKET_T clientfd = 0; int argc = 0; char** argv = 0; set_args(argc, argv, *static_cast<func_args*>(args)); tcp_accept(sockfd, clientfd, *static_cast<func_args*>(args)); -#ifdef _WIN32 - closesocket(sockfd); -#else - close(sockfd); -#endif + tcp_close(sockfd); SSL_METHOD* method = TLSv1_server_method(); SSL_CTX* ctx = SSL_CTX_new(method); @@ -36,9 +41,11 @@ THREAD_RETURN YASSL_API server_test(void* args) SSL* ssl = SSL_new(ctx); SSL_set_fd(ssl, clientfd); - if (SSL_accept(ssl) != SSL_SUCCESS) err_sys("SSL_accept failed"); + if (SSL_accept(ssl) != SSL_SUCCESS) + ServerError(ctx, ssl, clientfd, "SSL_accept failed"); + showPeer(ssl); - printf("Using Cipher Suite %s\n", SSL_get_cipher(ssl)); + printf("Using Cipher Suite: %s\n", SSL_get_cipher(ssl)); char command[1024]; command[SSL_read(ssl, command, sizeof(command))] = 0; @@ -46,12 +53,14 @@ THREAD_RETURN YASSL_API server_test(void* args) char msg[] = "I hear you, fa shizzle!"; if (SSL_write(ssl, msg, sizeof(msg)) != sizeof(msg)) - err_sys("SSL_write failed"); + ServerError(ctx, ssl, clientfd, "SSL_write failed"); DH_free(dh); SSL_CTX_free(ctx); SSL_free(ssl); + tcp_close(clientfd); + ((func_args*)args)->return_code = 0; return 0; } diff --git a/extra/yassl/include/buffer.hpp b/extra/yassl/include/buffer.hpp index 4816f79a9bc..c2709a8c847 100644 --- a/extra/yassl/include/buffer.hpp +++ b/extra/yassl/include/buffer.hpp @@ -34,7 +34,10 @@ #include <assert.h> // assert #include "yassl_types.hpp" // ysDelete #include "memory.hpp" // mySTL::auto_ptr -#include "algorithm.hpp" // mySTL::swap +#include STL_ALGORITHM_FILE + + +namespace STL = STL_NAMESPACE; #ifdef _MSC_VER @@ -199,7 +202,7 @@ struct del_ptr_zero void operator()(T*& p) const { T* tmp = 0; - mySTL::swap(tmp, p); + STL::swap(tmp, p); checked_delete(tmp); } }; diff --git a/extra/yassl/include/cert_wrapper.hpp b/extra/yassl/include/cert_wrapper.hpp index 8b5b7491772..761be0e9b04 100644 --- a/extra/yassl/include/cert_wrapper.hpp +++ b/extra/yassl/include/cert_wrapper.hpp @@ -41,8 +41,12 @@ #include "yassl_types.hpp" // SignatureAlgorithm #include "buffer.hpp" // input_buffer #include "asn.hpp" // SignerList -#include "list.hpp" // mySTL::list -#include "algorithm.hpp" // mySTL::for_each +#include STL_LIST_FILE +#include STL_ALGORITHM_FILE + + +namespace STL = STL_NAMESPACE; + namespace yaSSL { @@ -72,7 +76,7 @@ private: // Certificate Manager keeps a list of the cert chain and public key class CertManager { - typedef mySTL::list<x509*> CertList; + typedef STL::list<x509*> CertList; CertList list_; // self input_buffer privateKey_; @@ -120,6 +124,7 @@ public: void setVerifyNone(); void setFailNoCert(); void setSendVerify(); + void setPeerX509(X509*); private: CertManager(const CertManager&); // hide copy CertManager& operator=(const CertManager&); // and assign diff --git a/extra/yassl/include/crypto_wrapper.hpp b/extra/yassl/include/crypto_wrapper.hpp index 4c4e4d5da5b..83cf3d26398 100644 --- a/extra/yassl/include/crypto_wrapper.hpp +++ b/extra/yassl/include/crypto_wrapper.hpp @@ -416,7 +416,17 @@ private: class x509; -x509* PemToDer(FILE*, CertType); +struct EncryptedInfo { + enum { IV_SZ = 32, NAME_SZ = 80 }; + char name[NAME_SZ]; // max one line + byte iv[IV_SZ]; // in base16 rep + uint ivSz; + bool set; + + EncryptedInfo() : ivSz(0), set(false) {} +}; + +x509* PemToDer(FILE*, CertType, EncryptedInfo* info = 0); } // naemspace diff --git a/extra/yassl/include/factory.hpp b/extra/yassl/include/factory.hpp index 5619e90cd62..04d742431dc 100644 --- a/extra/yassl/include/factory.hpp +++ b/extra/yassl/include/factory.hpp @@ -35,10 +35,12 @@ #ifndef yaSSL_FACTORY_HPP #define yaSSL_FACTORY_HPP -#include "vector.hpp" -#include "pair.hpp" +#include STL_VECTOR_FILE +#include STL_PAIR_FILE +namespace STL = STL_NAMESPACE; + // VC60 workaround: it doesn't allow typename in some places #if defined(_MSC_VER) && (_MSC_VER < 1300) @@ -58,8 +60,8 @@ template<class AbstractProduct, typename ProductCreator = AbstractProduct* (*)() > class Factory { - typedef mySTL::pair<IdentifierType, ProductCreator> CallBack; - typedef mySTL::vector<CallBack> CallBackVector; + typedef STL::pair<IdentifierType, ProductCreator> CallBack; + typedef STL::vector<CallBack> CallBackVector; CallBackVector callbacks_; public: @@ -79,14 +81,16 @@ public: // register callback void Register(const IdentifierType& id, ProductCreator pc) { - callbacks_.push_back(mySTL::make_pair(id, pc)); + callbacks_.push_back(STL::make_pair(id, pc)); } // THE Creator, returns a new object of the proper type or 0 AbstractProduct* CreateObject(const IdentifierType& id) const { - const CallBack* first = callbacks_.begin(); - const CallBack* last = callbacks_.end(); + typedef typename STL::vector<CallBack>::const_iterator cIter; + + cIter first = callbacks_.begin(); + cIter last = callbacks_.end(); while (first != last) { if (first->first == id) diff --git a/extra/yassl/include/openssl/ssl.h b/extra/yassl/include/openssl/ssl.h index 47b4d075894..5e7290d2a7a 100644 --- a/extra/yassl/include/openssl/ssl.h +++ b/extra/yassl/include/openssl/ssl.h @@ -41,7 +41,7 @@ #include "rsa.h" -#define YASSL_VERSION "1.3.7" +#define YASSL_VERSION "1.4.3" #if defined(__cplusplus) @@ -505,6 +505,8 @@ ASN1_TIME* X509_get_notAfter(X509* x); #define V_ASN1_UTF8STRING 12 #define GEN_DNS 2 +#define CERTFICATE_ERROR 0x14090086 /* SSLv3 error */ + typedef struct MD4_CTX { int buffer[32]; /* big enough to hold, check size in Init */ diff --git a/extra/yassl/include/socket_wrapper.hpp b/extra/yassl/include/socket_wrapper.hpp index 1dd61b63148..9fc0d62f90e 100644 --- a/extra/yassl/include/socket_wrapper.hpp +++ b/extra/yassl/include/socket_wrapper.hpp @@ -71,6 +71,7 @@ typedef unsigned char byte; class Socket { socket_t socket_; // underlying socket descriptor bool wouldBlock_; // for non-blocking data + bool blocking_; // is option set public: explicit Socket(socket_t s = INVALID_SOCKET); ~Socket(); @@ -84,6 +85,7 @@ public: bool wait(); bool WouldBlock() const; + bool IsBlocking() const; void closeSocket(); void shutDown(int how = SD_SEND); diff --git a/extra/yassl/include/yassl_error.hpp b/extra/yassl/include/yassl_error.hpp index 3c3d5fa5231..72b79b05dbd 100644 --- a/extra/yassl/include/yassl_error.hpp +++ b/extra/yassl/include/yassl_error.hpp @@ -54,7 +54,11 @@ enum YasslError { verify_error = 112, send_error = 113, receive_error = 114, - certificate_error = 115 + certificate_error = 115, + privateKey_error = 116, + badVersion_error = 117 + + // !!!! add error message to .cpp !!!! // 1000+ from TaoCrypt error.hpp diff --git a/extra/yassl/include/yassl_imp.hpp b/extra/yassl/include/yassl_imp.hpp index 6e475c23db8..180d7fe7fe1 100644 --- a/extra/yassl/include/yassl_imp.hpp +++ b/extra/yassl/include/yassl_imp.hpp @@ -39,7 +39,10 @@ #include "yassl_types.hpp" #include "factory.hpp" -#include "list.hpp" // mySTL::list +#include STL_LIST_FILE + + +namespace STL = STL_NAMESPACE; namespace yaSSL { @@ -427,7 +430,7 @@ private: class CertificateRequest : public HandShakeBase { ClientCertificateType certificate_types_[CERT_TYPES]; int typeTotal_; - mySTL::list<DistinguishedName> certificate_authorities_; + STL::list<DistinguishedName> certificate_authorities_; public: CertificateRequest(); ~CertificateRequest(); diff --git a/extra/yassl/include/yassl_int.hpp b/extra/yassl/include/yassl_int.hpp index 26900aed3af..28e9d237622 100644 --- a/extra/yassl/include/yassl_int.hpp +++ b/extra/yassl/include/yassl_int.hpp @@ -40,6 +40,13 @@ #include "lock.hpp" #include "openssl/ssl.h" // ASN1_STRING and DH +#ifdef _POSIX_THREADS + #include <pthread.h> +#endif + + +namespace STL = STL_NAMESPACE; + namespace yaSSL { @@ -80,12 +87,35 @@ enum ServerState { }; +// client connect state for nonblocking restart +enum ConnectState { + CONNECT_BEGIN = 0, + CLIENT_HELLO_SENT, + FIRST_REPLY_DONE, + FINISHED_DONE, + SECOND_REPLY_DONE +}; + + +// server accpet state for nonblocking restart +enum AcceptState { + ACCEPT_BEGIN = 0, + ACCEPT_FIRST_REPLY_DONE, + SERVER_HELLO_DONE, + ACCEPT_SECOND_REPLY_DONE, + ACCEPT_FINISHED_DONE, + ACCEPT_THIRD_REPLY_DONE +}; + + // combines all states class States { RecordLayerState recordLayer_; HandShakeState handshakeLayer_; ClientState clientState_; ServerState serverState_; + ConnectState connectState_; + AcceptState acceptState_; char errorString_[MAX_ERROR_SZ]; YasslError what_; public: @@ -95,6 +125,8 @@ public: const HandShakeState& getHandShake() const; const ClientState& getClient() const; const ServerState& getServer() const; + const ConnectState& GetConnect() const; + const AcceptState& GetAccept() const; const char* getString() const; YasslError What() const; @@ -102,6 +134,8 @@ public: HandShakeState& useHandShake(); ClientState& useClient(); ServerState& useServer(); + ConnectState& UseConnect(); + AcceptState& UseAccept(); char* useString(); void SetError(YasslError); private: @@ -142,8 +176,9 @@ public: X509_NAME(const char*, size_t sz); ~X509_NAME(); - char* GetName(); + const char* GetName() const; ASN1_STRING* GetEntry(int i); + size_t GetLength() const; private: X509_NAME(const X509_NAME&); // hide copy X509_NAME& operator=(const X509_NAME&); // and assign @@ -157,6 +192,9 @@ public: ~StringHolder(); ASN1_STRING* GetString(); +private: + StringHolder(const StringHolder&); // hide copy + StringHolder& operator=(const StringHolder&); // and assign }; @@ -176,6 +214,7 @@ public: ASN1_STRING* GetBefore(); ASN1_STRING* GetAfter(); + private: X509(const X509&); // hide copy X509& operator=(const X509&); // and assign @@ -202,6 +241,7 @@ class SSL_SESSION { uint bornOn_; // create time in seconds uint timeout_; // timeout in seconds RandomPool& random_; // will clean master secret + X509* peerX509_; public: explicit SSL_SESSION(RandomPool&); SSL_SESSION(const SSL&, RandomPool&); @@ -212,17 +252,20 @@ public: const Cipher* GetSuite() const; uint GetBornOn() const; uint GetTimeOut() const; + X509* GetPeerX509() const; void SetTimeOut(uint); SSL_SESSION& operator=(const SSL_SESSION&); // allow assign for resumption private: SSL_SESSION(const SSL_SESSION&); // hide copy + + void CopyX509(X509*); }; // holds all sessions class Sessions { - mySTL::list<SSL_SESSION*> list_; + STL::list<SSL_SESSION*> list_; RandomPool random_; // for session cleaning Mutex mutex_; // no-op for single threaded @@ -241,8 +284,42 @@ private: }; +#ifdef _POSIX_THREADS + typedef pthread_t THREAD_ID_T; +#else + typedef DWORD THREAD_ID_T; +#endif + +// thread error data +struct ThreadError { + THREAD_ID_T threadID_; + int errorID_; +}; + + +// holds all errors +class Errors { + STL::list<ThreadError> list_; + Mutex mutex_; + + Errors() {} // only GetErrors can create +public: + int Lookup(bool peek); // self lookup + void Add(int); + void Remove(); // remove self + + ~Errors() {} + + friend Errors& GetErrors(); // singleton creator +private: + Errors(const Errors&); // hide copy + Errors& operator=(const Errors); // and assign +}; + + Sessions& GetSessions(); // forward singletons sslFactory& GetSSL_Factory(); +Errors& GetErrors(); // openSSL method and context types @@ -252,8 +329,10 @@ class SSL_METHOD { bool verifyPeer_; // request or send certificate bool verifyNone_; // whether to verify certificate bool failNoCert_; + bool multipleProtocol_; // for SSLv23 compatibility public: - explicit SSL_METHOD(ConnectionEnd ce, ProtocolVersion pv); + SSL_METHOD(ConnectionEnd ce, ProtocolVersion pv, + bool multipleProtocol = false); ProtocolVersion getVersion() const; ConnectionEnd getSide() const; @@ -265,6 +344,7 @@ public: bool verifyPeer() const; bool verifyNone() const; bool failNoCert() const; + bool multipleProtocol() const; private: SSL_METHOD(const SSL_METHOD&); // hide copy SSL_METHOD& operator=(const SSL_METHOD&); // and assign @@ -334,7 +414,7 @@ private: // the SSL context class SSL_CTX { public: - typedef mySTL::list<x509*> CertList; + typedef STL::list<x509*> CertList; private: SSL_METHOD* method_; x509* certificate_; @@ -342,6 +422,8 @@ private: CertList caList_; Ciphers ciphers_; DH_Parms dhParms_; + pem_password_cb passwordCb_; + void* userData_; Stats stats_; Mutex mutex_; // for Stats public: @@ -354,12 +436,16 @@ public: const Ciphers& GetCiphers() const; const DH_Parms& GetDH_Parms() const; const Stats& GetStats() const; + pem_password_cb GetPasswordCb() const; + void* GetUserData() const; void setVerifyPeer(); void setVerifyNone(); void setFailNoCert(); bool SetCipherList(const char*); bool SetDH(const DH&); + void SetPasswordCb(pem_password_cb cb); + void SetUserData(void*); void IncrementStats(StatsField); void AddCA(x509* ca); @@ -434,13 +520,14 @@ private: // holds input and output buffers class Buffers { public: - typedef mySTL::list<input_buffer*> inputList; - typedef mySTL::list<output_buffer*> outputList; + typedef STL::list<input_buffer*> inputList; + typedef STL::list<output_buffer*> outputList; private: inputList dataList_; // list of users app data / handshake outputList handShakeList_; // buffered handshake msgs + input_buffer* rawInput_; // buffered raw input yet to process public: - Buffers() {} + Buffers(); ~Buffers(); const inputList& getData() const; @@ -448,6 +535,9 @@ public: inputList& useData(); outputList& useHandShake(); + + void SetRawInput(input_buffer*); // takes ownership + input_buffer* TakeRawInput(); // takes ownership private: Buffers(const Buffers&); // hide copy Buffers& operator=(const Buffers&); // and assign @@ -502,6 +592,7 @@ public: const sslFactory& getFactory() const; const Socket& getSocket() const; YasslError GetError() const; + bool GetMultiProtocol() const; Crypto& useCrypto(); Security& useSecurity(); @@ -509,6 +600,7 @@ public: sslHashes& useHashes(); Socket& useSocket(); Log& useLog(); + Buffers& useBuffers(); // sets void set_pending(Cipher suite); diff --git a/extra/yassl/include/yassl_types.hpp b/extra/yassl/include/yassl_types.hpp index b75a2a45302..e602ee180bf 100644 --- a/extra/yassl/include/yassl_types.hpp +++ b/extra/yassl/include/yassl_types.hpp @@ -38,6 +38,8 @@ namespace yaSSL { +#define YASSL_LIB + #ifdef YASSL_PURE_C @@ -76,7 +78,7 @@ namespace yaSSL { ::operator delete[](ptr, yaSSL::ys); } - #define NEW_YS new (ys) + #define NEW_YS new (yaSSL::ys) // to resolve compiler generated operator delete on base classes with // virtual destructors (when on stack), make sure doesn't get called @@ -122,6 +124,39 @@ typedef opaque byte; typedef unsigned int uint; +#ifdef USE_SYS_STL + // use system STL + #define STL_VECTOR_FILE <vector> + #define STL_LIST_FILE <list> + #define STL_ALGORITHM_FILE <algorithm> + #define STL_MEMORY_FILE <memory> + #define STL_PAIR_FILE <utility> + + #define STL_NAMESPACE std +#else + // use mySTL + #define STL_VECTOR_FILE "vector.hpp" + #define STL_LIST_FILE "list.hpp" + #define STL_ALGORITHM_FILE "algorithm.hpp" + #define STL_MEMORY_FILE "memory.hpp" + #define STL_PAIR_FILE "pair.hpp" + + #define STL_NAMESPACE mySTL +#endif + + +#ifdef min + #undef min +#endif + +template <typename T> +T min(T a, T b) +{ + return a < b ? a : b; +} + + + // all length constants in bytes const int ID_LEN = 32; // session id length const int SUITE_LEN = 2; // cipher suite length @@ -163,6 +198,7 @@ const int DES_BLOCK = 8; // DES is always fixed block size 8 const int DES_IV_SZ = DES_BLOCK; // Init Vector length for DES const int RC4_KEY_SZ = 16; // RC4 Key length const int AES_128_KEY_SZ = 16; // AES 128bit Key length +const int AES_192_KEY_SZ = 24; // AES 192bit Key length const int AES_256_KEY_SZ = 32; // AES 256bit Key length const int AES_BLOCK_SZ = 16; // AES 128bit block size, rfc 3268 const int AES_IV_SZ = AES_BLOCK_SZ; // AES Init Vector length diff --git a/extra/yassl/src/Makefile.am b/extra/yassl/src/Makefile.am index 2b3e1aea5f5..910bbbdd13f 100644 --- a/extra/yassl/src/Makefile.am +++ b/extra/yassl/src/Makefile.am @@ -1,4 +1,4 @@ -INCLUDES = -I../include -I../taocrypt/include -I../mySTL +INCLUDES = -I../include -I../taocrypt/include -I../taocrypt/mySTL noinst_LTLIBRARIES = libyassl.la libyassl_la_SOURCES = buffer.cpp cert_wrapper.cpp crypto_wrapper.cpp \ @@ -6,3 +6,7 @@ libyassl_la_SOURCES = buffer.cpp cert_wrapper.cpp crypto_wrapper.cpp \ template_instnt.cpp timer.cpp yassl_imp.cpp yassl_error.cpp yassl_int.cpp EXTRA_DIST = $(wildcard ../include/*.hpp) $(wildcard ../include/openssl/*.h) AM_CXXFLAGS = -DYASSL_PURE_C -DYASSL_PREFIX + +# Don't update the files from bitkeeper +%::SCCS/s.% + diff --git a/extra/yassl/src/cert_wrapper.cpp b/extra/yassl/src/cert_wrapper.cpp index 6ad0aa568ed..c3ae9c0c561 100644 --- a/extra/yassl/src/cert_wrapper.cpp +++ b/extra/yassl/src/cert_wrapper.cpp @@ -63,8 +63,8 @@ x509::x509(const x509& that) : length_(that.length_), void x509::Swap(x509& that) { - mySTL::swap(length_, that.length_); - mySTL::swap(buffer_, that.buffer_); + STL::swap(length_, that.length_); + STL::swap(buffer_, that.buffer_); } @@ -105,11 +105,11 @@ CertManager::~CertManager() { ysDelete(peerX509_); - mySTL::for_each(signers_.begin(), signers_.end(), del_ptr_zero()) ; + STL::for_each(signers_.begin(), signers_.end(), del_ptr_zero()) ; - mySTL::for_each(peerList_.begin(), peerList_.end(), del_ptr_zero()) ; + STL::for_each(peerList_.begin(), peerList_.end(), del_ptr_zero()) ; - mySTL::for_each(list_.begin(), list_.end(), del_ptr_zero()) ; + STL::for_each(list_.begin(), list_.end(), del_ptr_zero()) ; } @@ -242,7 +242,7 @@ uint CertManager::get_privateKeyLength() const // Validate the peer's certificate list, from root to peer (last to first) int CertManager::Validate() { - CertList::iterator last = peerList_.rbegin(); // fix this + CertList::reverse_iterator last = peerList_.rbegin(); int count = peerList_.size(); while ( count > 1 ) { @@ -255,7 +255,7 @@ int CertManager::Validate() const TaoCrypt::PublicKey& key = cert.GetPublicKey(); signers_.push_back(NEW_YS TaoCrypt::Signer(key.GetKey(), key.size(), cert.GetCommonName(), cert.GetHash())); - --last; + ++last; --count; } @@ -310,6 +310,23 @@ int CertManager::SetPrivateKey(const x509& key) } +// Store OpenSSL type peer's cert +void CertManager::setPeerX509(X509* x) +{ + assert(peerX509_ == 0); + if (x == 0) return; + + X509_NAME* issuer = x->GetIssuer(); + X509_NAME* subject = x->GetSubject(); + ASN1_STRING* before = x->GetBefore(); + ASN1_STRING* after = x->GetAfter(); + + peerX509_ = NEW_YS X509(issuer->GetName(), issuer->GetLength(), + subject->GetName(), subject->GetLength(), (const char*) before->data, + before->length, (const char*) after->data, after->length); +} + + #if defined(USE_CML_LIB) // Get the peer's certificate, extract and save public key diff --git a/extra/yassl/src/crypto_wrapper.cpp b/extra/yassl/src/crypto_wrapper.cpp index 799106ec7c0..7344a70b367 100644 --- a/extra/yassl/src/crypto_wrapper.cpp +++ b/extra/yassl/src/crypto_wrapper.cpp @@ -908,7 +908,7 @@ void DiffieHellman::get_parms(byte* bp, byte* bg, byte* bpub) const // convert PEM file to DER x509 type -x509* PemToDer(FILE* file, CertType type) +x509* PemToDer(FILE* file, CertType type, EncryptedInfo* info) { using namespace TaoCrypt; @@ -935,6 +935,37 @@ x509* PemToDer(FILE* file, CertType type) break; } + // remove encrypted header if there + if (fgets(line, sizeof(line), file)) { + char encHeader[] = "Proc-Type"; + if (strncmp(encHeader, line, strlen(encHeader)) == 0 && + fgets(line,sizeof(line), file)) { + + char* start = strstr(line, "DES"); + char* finish = strstr(line, ","); + if (!start) + start = strstr(line, "AES"); + + if (!info) return 0; + + if ( start && finish && (start < finish)) { + memcpy(info->name, start, finish - start); + info->name[finish - start] = 0; + memcpy(info->iv, finish + 1, sizeof(info->iv)); + + char* newline = strstr(line, "\r"); + if (!newline) newline = strstr(line, "\n"); + if (newline && (newline > finish)) { + info->ivSz = newline - (finish + 1); + info->set = true; + } + } + fgets(line,sizeof(line), file); // get blank line + begin = ftell(file); + } + + } + while(fgets(line, sizeof(line), file)) if (strncmp(footer, line, strlen(footer)) == 0) { foundEnd = true; @@ -956,7 +987,7 @@ x509* PemToDer(FILE* file, CertType type) Base64Decoder b64Dec(der); uint sz = der.size(); - mySTL::auto_ptr<x509> x(NEW_YS x509(sz), ysDelete); + mySTL::auto_ptr<x509> x(NEW_YS x509(sz)); memcpy(x->use_buffer(), der.get_buffer(), sz); return x.release(); diff --git a/extra/yassl/src/handshake.cpp b/extra/yassl/src/handshake.cpp index e93f5385b3d..25f36c4ea8c 100644 --- a/extra/yassl/src/handshake.cpp +++ b/extra/yassl/src/handshake.cpp @@ -37,7 +37,6 @@ namespace yaSSL { -using mySTL::min; // Build a client hello message from cipher suites and compression method @@ -363,7 +362,7 @@ void p_hash(output_buffer& result, const output_buffer& secret, uint lastLen = result.get_capacity() % len; opaque previous[SHA_LEN]; // max size opaque current[SHA_LEN]; // max size - mySTL::auto_ptr<Digest> hmac(ysDelete); + mySTL::auto_ptr<Digest> hmac; if (lastLen) times += 1; @@ -582,7 +581,7 @@ void hmac(SSL& ssl, byte* digest, const byte* buffer, uint sz, void TLS_hmac(SSL& ssl, byte* digest, const byte* buffer, uint sz, ContentType content, bool verify) { - mySTL::auto_ptr<Digest> hmac(ysDelete); + mySTL::auto_ptr<Digest> hmac; opaque seq[SEQ_SZ] = { 0x00, 0x00, 0x00, 0x00 }; opaque length[LENGTH_SZ]; opaque inner[SIZEOF_ENUM + VERSION_SZ + LENGTH_SZ]; // type + version + len @@ -660,25 +659,25 @@ void build_certHashes(SSL& ssl, Hashes& hashes) -// do process input requests -mySTL::auto_ptr<input_buffer> -DoProcessReply(SSL& ssl, mySTL::auto_ptr<input_buffer> buffered) +// do process input requests, return 0 is done, 1 is call again to complete +int DoProcessReply(SSL& ssl) { // wait for input if blocking if (!ssl.useSocket().wait()) { ssl.SetError(receive_error); - buffered.reset(0); - return buffered; + return 0; } uint ready = ssl.getSocket().get_ready(); - if (!ready) return buffered; + if (!ready) return 1; // add buffered data if its there - uint buffSz = buffered.get() ? buffered.get()->get_size() : 0; + input_buffer* buffered = ssl.useBuffers().TakeRawInput(); + uint buffSz = buffered ? buffered->get_size() : 0; input_buffer buffer(buffSz + ready); if (buffSz) { - buffer.assign(buffered.get()->get_buffer(), buffSz); - buffered.reset(0); + buffer.assign(buffered->get_buffer(), buffSz); + ysDelete(buffered); + buffered = 0; } // add new data @@ -692,10 +691,8 @@ DoProcessReply(SSL& ssl, mySTL::auto_ptr<input_buffer> buffered) ssl.getStates().getServer() == clientNull) if (buffer.peek() != handshake) { ProcessOldClientHello(buffer, ssl); - if (ssl.GetError()) { - buffered.reset(0); - return buffered; - } + if (ssl.GetError()) + return 0; } while(!buffer.eof()) { @@ -715,31 +712,28 @@ DoProcessReply(SSL& ssl, mySTL::auto_ptr<input_buffer> buffered) // put header in front for next time processing uint extra = needHdr ? 0 : RECORD_HEADER; uint sz = buffer.get_remaining() + extra; - buffered.reset(NEW_YS input_buffer(sz, buffer.get_buffer() + - buffer.get_current() - extra, sz)); - break; + ssl.useBuffers().SetRawInput(NEW_YS input_buffer(sz, + buffer.get_buffer() + buffer.get_current() - extra, sz)); + return 1; } while (buffer.get_current() < hdr.length_ + RECORD_HEADER + offset) { // each message in record, can be more than 1 if not encrypted if (ssl.getSecurity().get_parms().pending_ == false) // cipher on decrypt_message(ssl, buffer, hdr.length_); - mySTL::auto_ptr<Message> msg(mf.CreateObject(hdr.type_), ysDelete); + mySTL::auto_ptr<Message> msg(mf.CreateObject(hdr.type_)); if (!msg.get()) { ssl.SetError(factory_error); - buffered.reset(0); - return buffered; + return 0; } buffer >> *msg; msg->Process(buffer, ssl); - if (ssl.GetError()) { - buffered.reset(0); - return buffered; - } + if (ssl.GetError()) + return 0; } offset += hdr.length_ + RECORD_HEADER; } - return buffered; + return 0; } @@ -747,16 +741,17 @@ DoProcessReply(SSL& ssl, mySTL::auto_ptr<input_buffer> buffered) void processReply(SSL& ssl) { if (ssl.GetError()) return; - mySTL::auto_ptr<input_buffer> buffered(ysDelete); - for (;;) { - mySTL::auto_ptr<input_buffer> tmp(DoProcessReply(ssl, buffered)); - if (tmp.get()) // had only part of a record's data, call again - buffered = tmp; - else - break; - if (ssl.GetError()) return; + if (DoProcessReply(ssl)) + // didn't complete process + if (!ssl.getSocket().IsBlocking()) { + // keep trying now + while (!ssl.GetError()) + if (DoProcessReply(ssl) == 0) break; } + else + // user will have try again later + ssl.SetError(YasslError(SSL_ERROR_WANT_READ)); } @@ -793,7 +788,7 @@ void sendClientKeyExchange(SSL& ssl, BufferOutput buffer) RecordLayerHeader rlHeader; HandShakeHeader hsHeader; - mySTL::auto_ptr<output_buffer> out(NEW_YS output_buffer, ysDelete); + mySTL::auto_ptr<output_buffer> out(NEW_YS output_buffer); buildHeaders(ssl, hsHeader, rlHeader, ck); buildOutput(*out.get(), rlHeader, hsHeader, ck); hashHandShake(ssl, *out.get()); @@ -814,7 +809,7 @@ void sendServerKeyExchange(SSL& ssl, BufferOutput buffer) RecordLayerHeader rlHeader; HandShakeHeader hsHeader; - mySTL::auto_ptr<output_buffer> out(NEW_YS output_buffer, ysDelete); + mySTL::auto_ptr<output_buffer> out(NEW_YS output_buffer); buildHeaders(ssl, hsHeader, rlHeader, sk); buildOutput(*out.get(), rlHeader, hsHeader, sk); hashHandShake(ssl, *out.get()); @@ -839,7 +834,7 @@ void sendChangeCipher(SSL& ssl, BufferOutput buffer) ChangeCipherSpec ccs; RecordLayerHeader rlHeader; buildHeader(ssl, rlHeader, ccs); - mySTL::auto_ptr<output_buffer> out(NEW_YS output_buffer, ysDelete); + mySTL::auto_ptr<output_buffer> out(NEW_YS output_buffer); buildOutput(*out.get(), rlHeader, ccs); if (buffer == buffered) @@ -856,7 +851,7 @@ void sendFinished(SSL& ssl, ConnectionEnd side, BufferOutput buffer) Finished fin; buildFinished(ssl, fin, side == client_end ? client : server); - mySTL::auto_ptr<output_buffer> out(NEW_YS output_buffer, ysDelete); + mySTL::auto_ptr<output_buffer> out(NEW_YS output_buffer); cipherFinished(ssl, fin, *out.get()); // hashes handshake if (ssl.getSecurity().get_resuming()) { @@ -955,7 +950,7 @@ void sendServerHello(SSL& ssl, BufferOutput buffer) ServerHello sh(ssl.getSecurity().get_connection().version_); RecordLayerHeader rlHeader; HandShakeHeader hsHeader; - mySTL::auto_ptr<output_buffer> out(NEW_YS output_buffer, ysDelete); + mySTL::auto_ptr<output_buffer> out(NEW_YS output_buffer); buildServerHello(ssl, sh); ssl.set_random(sh.get_random(), server_end); @@ -978,7 +973,7 @@ void sendServerHelloDone(SSL& ssl, BufferOutput buffer) ServerHelloDone shd; RecordLayerHeader rlHeader; HandShakeHeader hsHeader; - mySTL::auto_ptr<output_buffer> out(NEW_YS output_buffer, ysDelete); + mySTL::auto_ptr<output_buffer> out(NEW_YS output_buffer); buildHeaders(ssl, hsHeader, rlHeader, shd); buildOutput(*out.get(), rlHeader, hsHeader, shd); @@ -999,7 +994,7 @@ void sendCertificate(SSL& ssl, BufferOutput buffer) Certificate cert(ssl.getCrypto().get_certManager().get_cert()); RecordLayerHeader rlHeader; HandShakeHeader hsHeader; - mySTL::auto_ptr<output_buffer> out(NEW_YS output_buffer, ysDelete); + mySTL::auto_ptr<output_buffer> out(NEW_YS output_buffer); buildHeaders(ssl, hsHeader, rlHeader, cert); buildOutput(*out.get(), rlHeader, hsHeader, cert); @@ -1021,7 +1016,7 @@ void sendCertificateRequest(SSL& ssl, BufferOutput buffer) request.Build(); RecordLayerHeader rlHeader; HandShakeHeader hsHeader; - mySTL::auto_ptr<output_buffer> out(NEW_YS output_buffer, ysDelete); + mySTL::auto_ptr<output_buffer> out(NEW_YS output_buffer); buildHeaders(ssl, hsHeader, rlHeader, request); buildOutput(*out.get(), rlHeader, hsHeader, request); @@ -1043,7 +1038,7 @@ void sendCertificateVerify(SSL& ssl, BufferOutput buffer) verify.Build(ssl); RecordLayerHeader rlHeader; HandShakeHeader hsHeader; - mySTL::auto_ptr<output_buffer> out(NEW_YS output_buffer, ysDelete); + mySTL::auto_ptr<output_buffer> out(NEW_YS output_buffer); buildHeaders(ssl, hsHeader, rlHeader, verify); buildOutput(*out.get(), rlHeader, hsHeader, verify); diff --git a/extra/yassl/src/socket_wrapper.cpp b/extra/yassl/src/socket_wrapper.cpp index 7790001fc2d..70944831884 100644 --- a/extra/yassl/src/socket_wrapper.cpp +++ b/extra/yassl/src/socket_wrapper.cpp @@ -41,9 +41,10 @@ #include <netinet/in.h> #include <sys/ioctl.h> #include <string.h> + #include <fcntl.h> #endif // _WIN32 -#if defined(__sun) || defined(__SCO_VERSION__) +#if defined(__sun) || defined(__SCO_VERSION__) || defined(__NETWARE__) #include <sys/filio.h> #endif @@ -62,7 +63,7 @@ namespace yaSSL { Socket::Socket(socket_t s) - : socket_(s), wouldBlock_(false) + : socket_(s), wouldBlock_(false), blocking_(false) {} @@ -148,6 +149,7 @@ uint Socket::receive(byte* buf, unsigned int sz, int flags) if (get_lastError() == SOCKET_EWOULDBLOCK || get_lastError() == SOCKET_EAGAIN) { wouldBlock_ = true; + blocking_ = true; // socket can block, only way to tell for win32 return 0; } } @@ -189,6 +191,12 @@ bool Socket::WouldBlock() const } +bool Socket::IsBlocking() const +{ + return blocking_; +} + + void Socket::set_lastError(int errorCode) { #ifdef _WIN32 diff --git a/extra/yassl/src/ssl.cpp b/extra/yassl/src/ssl.cpp index 81e585ff735..a008ea7228b 100644 --- a/extra/yassl/src/ssl.cpp +++ b/extra/yassl/src/ssl.cpp @@ -42,6 +42,9 @@ #include "yassl_int.hpp" #include "md5.hpp" // for TaoCrypt MD5 size assert #include "md4.hpp" // for TaoCrypt MD4 size assert +#include "file.hpp" // for TaoCrypt Source +#include "coding.hpp" // HexDecoder +#include "helpers.hpp" // for placement new hack #include <stdio.h> #ifdef _WIN32 @@ -55,7 +58,6 @@ namespace yaSSL { -using mySTL::min; int read_file(SSL_CTX* ctx, const char* file, int format, CertType type) @@ -93,11 +95,55 @@ int read_file(SSL_CTX* ctx, const char* file, int format, CertType type) } } else { - x = PemToDer(input, type); + EncryptedInfo info; + x = PemToDer(input, type, &info); if (!x) { fclose(input); return SSL_BAD_FILE; } + if (info.set) { + // decrypt + char password[80]; + pem_password_cb cb = ctx->GetPasswordCb(); + if (!cb) { + fclose(input); + return SSL_BAD_FILE; + } + int passwordSz = cb(password, sizeof(password), 0, + ctx->GetUserData()); + byte key[AES_256_KEY_SZ]; // max sizes + byte iv[AES_IV_SZ]; + + // use file's salt for key derivation, but not real iv + TaoCrypt::Source source(info.iv, info.ivSz); + TaoCrypt::HexDecoder dec(source); + memcpy(info.iv, source.get_buffer(), min((uint)sizeof(info.iv), + source.size())); + EVP_BytesToKey(info.name, "MD5", info.iv, (byte*)password, + passwordSz, 1, key, iv); + + STL::auto_ptr<BulkCipher> cipher; + if (strncmp(info.name, "DES-CBC", 7) == 0) + cipher.reset(NEW_YS DES); + else if (strncmp(info.name, "DES-EDE3-CBC", 13) == 0) + cipher.reset(NEW_YS DES_EDE); + else if (strncmp(info.name, "AES-128-CBC", 13) == 0) + cipher.reset(NEW_YS AES(AES_128_KEY_SZ)); + else if (strncmp(info.name, "AES-192-CBC", 13) == 0) + cipher.reset(NEW_YS AES(AES_192_KEY_SZ)); + else if (strncmp(info.name, "AES-256-CBC", 13) == 0) + cipher.reset(NEW_YS AES(AES_256_KEY_SZ)); + else { + fclose(input); + return SSL_BAD_FILE; + } + cipher->set_decryptKey(key, info.iv); + STL::auto_ptr<x509> newx(NEW_YS x509(x->get_length())); + cipher->decrypt(newx->use_buffer(), x->get_buffer(), + x->get_length()); + ysDelete(x); + x = newx.release(); + } } } fclose(input); @@ -140,8 +186,17 @@ SSL_METHOD* TLSv1_client_method() SSL_METHOD* SSLv23_server_method() { - // compatibility only, no version 2 support - return SSLv3_server_method(); + // compatibility only, no version 2 support, but does SSL 3 and TLS 1 + return NEW_YS SSL_METHOD(server_end, ProtocolVersion(3,1), true); +} + + +SSL_METHOD* SSLv23_client_method() +{ + // compatibility only, no version 2 support, but does SSL 3 and TLS 1 + // though it sends TLS1 hello not SSLv2 so SSLv3 only servers will decline + // TODO: maybe add support to send SSLv2 hello ??? + return NEW_YS SSL_METHOD(client_end, ProtocolVersion(3,1), true); } @@ -178,14 +233,29 @@ int SSL_set_fd(SSL* ssl, int fd) int SSL_connect(SSL* ssl) { + if (ssl->GetError() == YasslError(SSL_ERROR_WANT_READ)) + ssl->SetError(no_error); + + ClientState neededState; + + switch (ssl->getStates().GetConnect()) { + + case CONNECT_BEGIN : sendClientHello(*ssl); - ClientState neededState = ssl->getSecurity().get_resuming() ? + if (!ssl->GetError()) + ssl->useStates().UseConnect() = CLIENT_HELLO_SENT; + + case CLIENT_HELLO_SENT : + neededState = ssl->getSecurity().get_resuming() ? serverFinishedComplete : serverHelloDoneComplete; while (ssl->getStates().getClient() < neededState) { if (ssl->GetError()) break; processReply(*ssl); } + if (!ssl->GetError()) + ssl->useStates().UseConnect() = FIRST_REPLY_DONE; + case FIRST_REPLY_DONE : if(ssl->getCrypto().get_certManager().sendVerify()) sendCertificate(*ssl); @@ -198,18 +268,32 @@ int SSL_connect(SSL* ssl) sendChangeCipher(*ssl); sendFinished(*ssl, client_end); ssl->flushBuffer(); + + if (!ssl->GetError()) + ssl->useStates().UseConnect() = FINISHED_DONE; + + case FINISHED_DONE : if (!ssl->getSecurity().get_resuming()) while (ssl->getStates().getClient() < serverFinishedComplete) { if (ssl->GetError()) break; processReply(*ssl); } + if (!ssl->GetError()) + ssl->useStates().UseConnect() = SECOND_REPLY_DONE; + case SECOND_REPLY_DONE : ssl->verifyState(serverFinishedComplete); ssl->useLog().ShowTCP(ssl->getSocket().get_fd()); - if (ssl->GetError()) + if (ssl->GetError()) { + GetErrors().Add(ssl->GetError()); return SSL_FATAL_ERROR; + } return SSL_SUCCESS; + + default : + return SSL_FATAL_ERROR; // unkown state + } } @@ -228,7 +312,17 @@ int SSL_read(SSL* ssl, void* buffer, int sz) int SSL_accept(SSL* ssl) { + if (ssl->GetError() == YasslError(SSL_ERROR_WANT_READ)) + ssl->SetError(no_error); + + switch (ssl->getStates().GetAccept()) { + + case ACCEPT_BEGIN : processReply(*ssl); + if (!ssl->GetError()) + ssl->useStates().UseAccept() = ACCEPT_FIRST_REPLY_DONE; + + case ACCEPT_FIRST_REPLY_DONE : sendServerHello(*ssl); if (!ssl->getSecurity().get_resuming()) { @@ -242,27 +336,51 @@ int SSL_accept(SSL* ssl) sendServerHelloDone(*ssl); ssl->flushBuffer(); + } + + if (!ssl->GetError()) + ssl->useStates().UseAccept() = SERVER_HELLO_DONE; + case SERVER_HELLO_DONE : + if (!ssl->getSecurity().get_resuming()) { while (ssl->getStates().getServer() < clientFinishedComplete) { if (ssl->GetError()) break; processReply(*ssl); } } + if (!ssl->GetError()) + ssl->useStates().UseAccept() = ACCEPT_SECOND_REPLY_DONE; + + case ACCEPT_SECOND_REPLY_DONE : sendChangeCipher(*ssl); sendFinished(*ssl, server_end); ssl->flushBuffer(); + + if (!ssl->GetError()) + ssl->useStates().UseAccept() = ACCEPT_FINISHED_DONE; + + case ACCEPT_FINISHED_DONE : if (ssl->getSecurity().get_resuming()) { while (ssl->getStates().getServer() < clientFinishedComplete) { if (ssl->GetError()) break; processReply(*ssl); } } + if (!ssl->GetError()) + ssl->useStates().UseAccept() = ACCEPT_THIRD_REPLY_DONE; + case ACCEPT_THIRD_REPLY_DONE : ssl->useLog().ShowTCP(ssl->getSocket().get_fd()); - if (ssl->GetError()) + if (ssl->GetError()) { + GetErrors().Add(ssl->GetError()); return SSL_FATAL_ERROR; + } return SSL_SUCCESS; + + default: + return SSL_FATAL_ERROR; // unknown state + } } @@ -278,6 +396,8 @@ int SSL_do_handshake(SSL* ssl) int SSL_clear(SSL* ssl) { ssl->useSocket().closeSocket(); + GetErrors().Remove(); + return SSL_SUCCESS; } @@ -289,6 +409,8 @@ int SSL_shutdown(SSL* ssl) ssl->useLog().ShowTCP(ssl->getSocket().get_fd(), true); ssl->useSocket().closeSocket(); + GetErrors().Remove(); + return SSL_SUCCESS; } @@ -762,9 +884,8 @@ void DH_free(DH* dh) // be created BIGNUM* BN_bin2bn(const unsigned char* num, int sz, BIGNUM* retVal) { - using mySTL::auto_ptr; bool created = false; - auto_ptr<BIGNUM> bn(ysDelete); + mySTL::auto_ptr<BIGNUM> bn; if (!retVal) { created = true; @@ -825,7 +946,7 @@ const EVP_MD* EVP_md5(void) const EVP_CIPHER* EVP_des_ede3_cbc(void) { - static const char* type = "DES_EDE3_CBC"; + static const char* type = "DES-EDE3-CBC"; return type; } @@ -836,16 +957,37 @@ int EVP_BytesToKey(const EVP_CIPHER* type, const EVP_MD* md, const byte* salt, // only support MD5 for now if (strncmp(md, "MD5", 3)) return 0; - // only support DES_EDE3_CBC for now - if (strncmp(type, "DES_EDE3_CBC", 12)) return 0; + int keyLen = 0; + int ivLen = 0; + + // only support CBC DES and AES for now + if (strncmp(type, "DES-CBC", 7) == 0) { + keyLen = DES_KEY_SZ; + ivLen = DES_IV_SZ; + } + else if (strncmp(type, "DES-EDE3-CBC", 12) == 0) { + keyLen = DES_EDE_KEY_SZ; + ivLen = DES_IV_SZ; + } + else if (strncmp(type, "AES-128-CBC", 11) == 0) { + keyLen = AES_128_KEY_SZ; + ivLen = AES_IV_SZ; + } + else if (strncmp(type, "AES-192-CBC", 11) == 0) { + keyLen = AES_192_KEY_SZ; + ivLen = AES_IV_SZ; + } + else if (strncmp(type, "AES-256-CBC", 11) == 0) { + keyLen = AES_256_KEY_SZ; + ivLen = AES_IV_SZ; + } + else + return 0; yaSSL::MD5 myMD; uint digestSz = myMD.get_digestSize(); byte digest[SHA_LEN]; // max size - yaSSL::DES_EDE cipher; - int keyLen = cipher.get_keySize(); - int ivLen = cipher.get_ivSize(); int keyLeft = keyLen; int ivLeft = ivLen; int keyOutput = 0; @@ -878,7 +1020,7 @@ int EVP_BytesToKey(const EVP_CIPHER* type, const EVP_MD* md, const byte* salt, if (ivLeft && digestLeft) { int store = min(ivLeft, digestLeft); - memcpy(&iv[ivLen - ivLeft], digest, store); + memcpy(&iv[ivLen - ivLeft], &digest[digestSz - digestLeft], store); keyOutput += store; ivLeft -= store; @@ -954,10 +1096,9 @@ void DES_ecb_encrypt(DES_cblock* input, DES_cblock* output, } -void SSL_CTX_set_default_passwd_cb_userdata(SSL_CTX*, void* userdata) +void SSL_CTX_set_default_passwd_cb_userdata(SSL_CTX* ctx, void* userdata) { - // yaSSL doesn't support yet, unencrypt your PEM file with userdata - // before handing off to yaSSL + ctx->SetUserData(userdata); } @@ -1034,12 +1175,6 @@ ASN1_TIME* X509_get_notAfter(X509* x) } -SSL_METHOD* SSLv23_client_method(void) /* doesn't actually roll back */ -{ - return SSLv3_client_method(); -} - - SSL_METHOD* SSLv2_client_method(void) /* will never work, no v 2 */ { return 0; @@ -1363,9 +1498,9 @@ int SSL_pending(SSL* ssl) } - void SSL_CTX_set_default_passwd_cb(SSL_CTX*, pem_password_cb) + void SSL_CTX_set_default_passwd_cb(SSL_CTX* ctx, pem_password_cb cb) { - // TDOD: + ctx->SetPasswordCb(cb); } @@ -1428,7 +1563,7 @@ int SSL_pending(SSL* ssl) void ERR_remove_state(unsigned long) { - // TODO: + GetErrors().Remove(); } @@ -1437,16 +1572,30 @@ int SSL_pending(SSL* ssl) return l & 0xfff; } + unsigned long err_helper(bool peek = false) + { + int ysError = GetErrors().Lookup(peek); + + // translate cert error for libcurl, it uses OpenSSL hex code + switch (ysError) { + case TaoCrypt::SIG_OTHER_E: + return CERTFICATE_ERROR; + break; + default : + return 0; + } + } + unsigned long ERR_peek_error() { - return 0; // TODO: + return err_helper(true); } unsigned long ERR_get_error() { - return ERR_peek_error(); + return err_helper(); } diff --git a/extra/yassl/src/template_instnt.cpp b/extra/yassl/src/template_instnt.cpp index c5fc23dabdb..fb488e47672 100644 --- a/extra/yassl/src/template_instnt.cpp +++ b/extra/yassl/src/template_instnt.cpp @@ -65,6 +65,19 @@ template yaSSL::del_ptr_zero for_each<mySTL::list<yaSSL::output_buffer*>::iterat template yaSSL::del_ptr_zero for_each<mySTL::list<yaSSL::x509*>::iterator, yaSSL::del_ptr_zero>(mySTL::list<yaSSL::x509*>::iterator, mySTL::list<yaSSL::x509*>::iterator, yaSSL::del_ptr_zero); template yaSSL::del_ptr_zero for_each<mySTL::list<yaSSL::Digest*>::iterator, yaSSL::del_ptr_zero>(mySTL::list<yaSSL::Digest*>::iterator, mySTL::list<yaSSL::Digest*>::iterator, yaSSL::del_ptr_zero); template yaSSL::del_ptr_zero for_each<mySTL::list<yaSSL::BulkCipher*>::iterator, yaSSL::del_ptr_zero>(mySTL::list<yaSSL::BulkCipher*>::iterator, mySTL::list<yaSSL::BulkCipher*>::iterator, yaSSL::del_ptr_zero); +template bool list<yaSSL::ThreadError>::erase(list<yaSSL::ThreadError>::iterator); +template void list<yaSSL::ThreadError>::push_back(yaSSL::ThreadError); +template void list<yaSSL::ThreadError>::pop_front(); +template void list<yaSSL::ThreadError>::pop_back(); +template list<yaSSL::ThreadError>::~list(); +template pair<int, yaSSL::Message* (*)()>* GetArrayMemory<pair<int, yaSSL::Message* (*)()> >(size_t); +template void FreeArrayMemory<pair<int, yaSSL::Message* (*)()> >(pair<int, yaSSL::Message* (*)()>*); +template pair<int, yaSSL::HandShakeBase* (*)()>* GetArrayMemory<pair<int, yaSSL::HandShakeBase* (*)()> >(size_t); +template void FreeArrayMemory<pair<int, yaSSL::HandShakeBase* (*)()> >(pair<int, yaSSL::HandShakeBase* (*)()>*); +template pair<int, yaSSL::ServerKeyBase* (*)()>* GetArrayMemory<pair<int, yaSSL::ServerKeyBase* (*)()> >(size_t); +template void FreeArrayMemory<pair<int, yaSSL::ServerKeyBase* (*)()> >(pair<int, yaSSL::ServerKeyBase* (*)()>*); +template pair<int, yaSSL::ClientKeyBase* (*)()>* GetArrayMemory<pair<int, yaSSL::ClientKeyBase* (*)()> >(size_t); +template void FreeArrayMemory<pair<int, yaSSL::ClientKeyBase* (*)()> >(pair<int, yaSSL::ClientKeyBase* (*)()>*); } namespace yaSSL { @@ -90,8 +103,13 @@ template void ysDelete<X509>(X509*); template void ysDelete<Message>(Message*); template void ysDelete<sslFactory>(sslFactory*); template void ysDelete<Sessions>(Sessions*); +template void ysDelete<Errors>(Errors*); template void ysArrayDelete<unsigned char>(unsigned char*); template void ysArrayDelete<char>(char*); + +template int min<int>(int, int); +template unsigned int min<unsigned int>(unsigned int, unsigned int); +template unsigned long min<unsigned long>(unsigned long, unsigned long); } #endif // HAVE_EXPLICIT_TEMPLATE_INSTANTIATION diff --git a/extra/yassl/src/yassl.cpp b/extra/yassl/src/yassl.cpp index 5bc8bad8bbc..e253ef84bb5 100644 --- a/extra/yassl/src/yassl.cpp +++ b/extra/yassl/src/yassl.cpp @@ -36,21 +36,9 @@ #include "openssl/ssl.h" // get rid of this -// yaSSL overloads hide these -void* operator new[](size_t sz) -{ - return ::operator new(sz); -} - -void operator delete[](void* ptr) -{ - ::operator delete(ptr); -} - namespace yaSSL { -using mySTL::min; struct Base { diff --git a/extra/yassl/src/yassl_error.cpp b/extra/yassl/src/yassl_error.cpp index 4f75de34a98..3531c0a2c74 100644 --- a/extra/yassl/src/yassl_error.cpp +++ b/extra/yassl/src/yassl_error.cpp @@ -125,13 +125,21 @@ void SetErrorString(YasslError error, char* buffer) strncpy(buffer, "unable to proccess cerificate", max); break; + case privateKey_error : + strncpy(buffer, "unable to proccess private key, bad format", max); + break; + + case badVersion_error : + strncpy(buffer, "protocl version mismatch", max); + break; + // openssl errors case SSL_ERROR_WANT_READ : strncpy(buffer, "the read operation would block", max); break; // TaoCrypt errors - case NO_ERROR : + case NO_ERROR_E : strncpy(buffer, "not in error state", max); break; @@ -235,6 +243,10 @@ void SetErrorString(YasslError error, char* buffer) strncpy(buffer, "ASN: bad other signature confirmation", max); break; + case CERTFICATE_ERROR : + strncpy(buffer, "Unable to verify certificate", max); + break; + default : strncpy(buffer, "unknown error number", max); } diff --git a/extra/yassl/src/yassl_imp.cpp b/extra/yassl/src/yassl_imp.cpp index 98f8035732e..bd07f8b70f2 100644 --- a/extra/yassl/src/yassl_imp.cpp +++ b/extra/yassl/src/yassl_imp.cpp @@ -139,7 +139,7 @@ void DH_Server::build(SSL& ssl) parms_.alloc_pub(pubSz)); short sigSz = 0; - mySTL::auto_ptr<Auth> auth(ysDelete); + mySTL::auto_ptr<Auth> auth; const CertManager& cert = ssl.getCrypto().get_certManager(); if (ssl.getSecurity().get_parms().sig_algo_ == rsa_sa_algo) @@ -151,9 +151,11 @@ void DH_Server::build(SSL& ssl) sigSz += DSS_ENCODED_EXTRA; } - sigSz += auth->get_signatureLength(); - + if (!sigSz) { + ssl.SetError(privateKey_error); + return; + } length_ = 8; // pLen + gLen + YsLen + SigLen length_ += pSz + gSz + pubSz + sigSz; @@ -612,7 +614,7 @@ void HandShakeHeader::Process(input_buffer& input, SSL& ssl) { ssl.verifyState(*this); const HandShakeFactory& hsf = ssl.getFactory().getHandShake(); - mySTL::auto_ptr<HandShakeBase> hs(hsf.CreateObject(type_), ysDelete); + mySTL::auto_ptr<HandShakeBase> hs(hsf.CreateObject(type_)); if (!hs.get()) { ssl.SetError(factory_error); return; @@ -1214,6 +1216,20 @@ output_buffer& operator<<(output_buffer& output, const ServerHello& hello) // Server Hello processing handler void ServerHello::Process(input_buffer&, SSL& ssl) { + if (ssl.GetMultiProtocol()) { // SSLv23 support + if (ssl.isTLS() && server_version_.minor_ < 1) + // downgrade to SSLv3 + ssl.useSecurity().use_connection().TurnOffTLS(); + } + else if (ssl.isTLS() && server_version_.minor_ < 1) { + ssl.SetError(badVersion_error); + return; + } + else if (!ssl.isTLS() && (server_version_.major_ == 3 && + server_version_.minor_ >= 1)) { + ssl.SetError(badVersion_error); + return; + } ssl.set_pending(cipher_suite_[1]); ssl.set_random(random_, server_end); if (id_len_) @@ -1384,11 +1400,23 @@ output_buffer& operator<<(output_buffer& output, const ClientHello& hello) // Client Hello processing handler void ClientHello::Process(input_buffer&, SSL& ssl) { - if (ssl.isTLS() && client_version_.minor_ == 0) { + if (ssl.GetMultiProtocol()) { // SSLv23 support + if (ssl.isTLS() && client_version_.minor_ < 1) { + // downgrade to SSLv3 ssl.useSecurity().use_connection().TurnOffTLS(); ProtocolVersion pv = ssl.getSecurity().get_connection().version_; ssl.useSecurity().use_parms().SetSuites(pv); // reset w/ SSL suites } + } + else if (ssl.isTLS() && client_version_.minor_ < 1) { + ssl.SetError(badVersion_error); + return; + } + else if (!ssl.isTLS() && (client_version_.major_ == 3 && + client_version_.minor_ >= 1)) { + ssl.SetError(badVersion_error); + return; + } ssl.set_random(random_, client_end); while (id_len_) { // trying to resume @@ -1541,7 +1569,7 @@ CertificateRequest::CertificateRequest() CertificateRequest::~CertificateRequest() { - mySTL::for_each(certificate_authorities_.begin(), + STL::for_each(certificate_authorities_.begin(), certificate_authorities_.end(), del_ptr_zero()) ; } @@ -1634,9 +1662,9 @@ output_buffer& operator<<(output_buffer& output, request.typeTotal_ - REQUEST_HEADER, tmp); output.write(tmp, sizeof(tmp)); - mySTL::list<DistinguishedName>::const_iterator first = + STL::list<DistinguishedName>::const_iterator first = request.certificate_authorities_.begin(); - mySTL::list<DistinguishedName>::const_iterator last = + STL::list<DistinguishedName>::const_iterator last = request.certificate_authorities_.end(); while (first != last) { uint16 sz; @@ -1684,7 +1712,7 @@ void CertificateVerify::Build(SSL& ssl) uint16 sz = 0; byte len[VERIFY_HEADER]; - mySTL::auto_ptr<byte> sig(ysArrayDelete); + mySTL::auto_array<byte> sig; // sign const CertManager& cert = ssl.getCrypto().get_certManager(); diff --git a/extra/yassl/src/yassl_int.cpp b/extra/yassl/src/yassl_int.cpp index 9b83f964348..5288acb2bcd 100644 --- a/extra/yassl/src/yassl_int.cpp +++ b/extra/yassl/src/yassl_int.cpp @@ -33,6 +33,10 @@ #include "handshake.hpp" #include "timer.hpp" +#ifdef _POSIX_THREADS + #include "pthread.h" +#endif + #ifdef YASSL_PURE_C @@ -74,7 +78,6 @@ namespace yaSSL { -using mySTL::min; @@ -155,6 +158,7 @@ void c32toa(uint32 u32, opaque* c) States::States() : recordLayer_(recordReady), handshakeLayer_(preHandshake), clientState_(serverNull), serverState_(clientNull), + connectState_(CONNECT_BEGIN), acceptState_(ACCEPT_BEGIN), what_(no_error) {} const RecordLayerState& States::getRecord() const @@ -181,6 +185,18 @@ const ServerState& States::getServer() const } +const ConnectState& States::GetConnect() const +{ + return connectState_; +} + + +const AcceptState& States::GetAccept() const +{ + return acceptState_; +} + + const char* States::getString() const { return errorString_; @@ -217,6 +233,18 @@ ServerState& States::useServer() } +ConnectState& States::UseConnect() +{ + return connectState_; +} + + +AcceptState& States::UseAccept() +{ + return acceptState_; +} + + char* States::useString() { return errorString_; @@ -722,6 +750,12 @@ void SSL::SetError(YasslError ye) } +Buffers& SSL::useBuffers() +{ + return buffers_; +} + + // locals namespace { @@ -959,7 +993,7 @@ using namespace yassl_int_cpp_local1; uint SSL::bufferedData() { - return mySTL::for_each(buffers_.getData().begin(),buffers_.getData().end(), + return STL::for_each(buffers_.getData().begin(),buffers_.getData().end(), SumData()).total_; } @@ -1002,7 +1036,7 @@ void SSL::PeekData(Data& data) data.set_length(0); // output, actual data filled dataSz = min(dataSz, bufferedData()); - Buffers::inputList::iterator front = buffers_.getData().begin(); + Buffers::inputList::iterator front = buffers_.useData().begin(); while (elements) { uint frontSz = (*front)->get_remaining(); @@ -1027,7 +1061,7 @@ void SSL::flushBuffer() { if (GetError()) return; - uint sz = mySTL::for_each(buffers_.getHandShake().begin(), + uint sz = STL::for_each(buffers_.getHandShake().begin(), buffers_.getHandShake().end(), SumBuffer()).total_; output_buffer out(sz); @@ -1213,8 +1247,10 @@ void SSL::matchSuite(const opaque* peer, uint length) void SSL::set_session(SSL_SESSION* s) { - if (s && GetSessions().lookup(s->GetID(), &secure_.use_resume())) + if (s && GetSessions().lookup(s->GetID(), &secure_.use_resume())) { secure_.set_resuming(true); + crypto_.use_certManager().setPeerX509(s->GetPeerX509()); + } } @@ -1260,6 +1296,12 @@ YasslError SSL::GetError() const } +bool SSL::GetMultiProtocol() const +{ + return secure_.GetContext()->getMethod()->multipleProtocol(); +} + + Crypto& SSL::useCrypto() { return crypto_; @@ -1314,9 +1356,25 @@ void SSL::addBuffer(output_buffer* b) } +void SSL_SESSION::CopyX509(X509* x) +{ + assert(peerX509_ == 0); + if (x == 0) return; + + X509_NAME* issuer = x->GetIssuer(); + X509_NAME* subject = x->GetSubject(); + ASN1_STRING* before = x->GetBefore(); + ASN1_STRING* after = x->GetAfter(); + + peerX509_ = NEW_YS X509(issuer->GetName(), issuer->GetLength(), + subject->GetName(), subject->GetLength(), (const char*) before->data, + before->length, (const char*) after->data, after->length); +} + + // store connection parameters SSL_SESSION::SSL_SESSION(const SSL& ssl, RandomPool& ran) - : timeout_(DEFAULT_TIMEOUT), random_(ran) + : timeout_(DEFAULT_TIMEOUT), random_(ran), peerX509_(0) { const Connection& conn = ssl.getSecurity().get_connection(); @@ -1325,12 +1383,14 @@ SSL_SESSION::SSL_SESSION(const SSL& ssl, RandomPool& ran) memcpy(suite_, ssl.getSecurity().get_parms().suite_, SUITE_LEN); bornOn_ = lowResTimer(); + + CopyX509(ssl.getCrypto().get_certManager().get_peerX509()); } // for resumption copy in ssl::parameters SSL_SESSION::SSL_SESSION(RandomPool& ran) - : bornOn_(0), timeout_(0), random_(ran) + : bornOn_(0), timeout_(0), random_(ran), peerX509_(0) { memset(sessionID_, 0, ID_LEN); memset(master_secret_, 0, SECRET_LEN); @@ -1347,6 +1407,12 @@ SSL_SESSION& SSL_SESSION::operator=(const SSL_SESSION& that) bornOn_ = that.bornOn_; timeout_ = that.timeout_; + if (peerX509_) { + ysDelete(peerX509_); + peerX509_ = 0; + } + CopyX509(that.peerX509_); + return *this; } @@ -1369,6 +1435,12 @@ const Cipher* SSL_SESSION::GetSuite() const } +X509* SSL_SESSION::GetPeerX509() const +{ + return peerX509_; +} + + uint SSL_SESSION::GetBornOn() const { return bornOn_; @@ -1395,6 +1467,8 @@ SSL_SESSION::~SSL_SESSION() { volatile opaque* p = master_secret_; clean(p, SECRET_LEN, random_); + + ysDelete(peerX509_); } @@ -1418,6 +1492,15 @@ sslFactory& GetSSL_Factory() } +static Errors* errorsInstance = 0; + +Errors& GetErrors() +{ + if (!errorsInstance) + errorsInstance = NEW_YS Errors; + return *errorsInstance; +} + typedef Mutex::Lock Lock; @@ -1433,14 +1516,15 @@ void Sessions::add(const SSL& ssl) Sessions::~Sessions() { - mySTL::for_each(list_.begin(), list_.end(), del_ptr_zero()); + STL::for_each(list_.begin(), list_.end(), del_ptr_zero()); } // locals namespace yassl_int_cpp_local2 { // for explicit templates -typedef mySTL::list<SSL_SESSION*>::iterator iterator; +typedef STL::list<SSL_SESSION*>::iterator sess_iterator; +typedef STL::list<ThreadError>::iterator thr_iterator; struct sess_match { const opaque* id_; @@ -1455,6 +1539,28 @@ struct sess_match { }; +THREAD_ID_T GetSelf() +{ +#ifndef _POSIX_THREADS + return GetCurrentThreadId(); +#else + return pthread_self(); +#endif +} + +struct thr_match { + THREAD_ID_T id_; + explicit thr_match() : id_(GetSelf()) {} + + bool operator()(ThreadError thr) + { + if (thr.threadID_ == id_) + return true; + return false; + } +}; + + } // local namespace using namespace yassl_int_cpp_local2; @@ -1463,8 +1569,8 @@ using namespace yassl_int_cpp_local2; SSL_SESSION* Sessions::lookup(const opaque* id, SSL_SESSION* copy) { Lock guard(mutex_); - iterator find = mySTL::find_if(list_.begin(), list_.end(), sess_match(id)); - + sess_iterator find = STL::find_if(list_.begin(), list_.end(), + sess_match(id)); if (find != list_.end()) { uint current = lowResTimer(); if ( ((*find)->GetBornOn() + (*find)->GetTimeOut()) < current) { @@ -1484,8 +1590,8 @@ SSL_SESSION* Sessions::lookup(const opaque* id, SSL_SESSION* copy) void Sessions::remove(const opaque* id) { Lock guard(mutex_); - iterator find = mySTL::find_if(list_.begin(), list_.end(), sess_match(id)); - + sess_iterator find = STL::find_if(list_.begin(), list_.end(), + sess_match(id)); if (find != list_.end()) { del_ptr_zero()(*find); list_.erase(find); @@ -1493,9 +1599,51 @@ void Sessions::remove(const opaque* id) } -SSL_METHOD::SSL_METHOD(ConnectionEnd ce, ProtocolVersion pv) +// remove a self thread error +void Errors::Remove() +{ + Lock guard(mutex_); + thr_iterator find = STL::find_if(list_.begin(), list_.end(), + thr_match()); + if (find != list_.end()) + list_.erase(find); +} + + +// lookup self error code +int Errors::Lookup(bool peek) +{ + Lock guard(mutex_); + thr_iterator find = STL::find_if(list_.begin(), list_.end(), + thr_match()); + if (find != list_.end()) { + int ret = find->errorID_; + if (!peek) + list_.erase(find); + return ret; + } + else + return 0; +} + + +// add a new error code for self +void Errors::Add(int error) +{ + ThreadError add; + add.errorID_ = error; + add.threadID_ = GetSelf(); + + Remove(); // may have old error + + Lock guard(mutex_); + list_.push_back(add); +} + + +SSL_METHOD::SSL_METHOD(ConnectionEnd ce, ProtocolVersion pv, bool multiProto) : version_(pv), side_(ce), verifyPeer_(false), verifyNone_(false), - failNoCert_(false) + failNoCert_(false), multipleProtocol_(multiProto) {} @@ -1547,8 +1695,15 @@ bool SSL_METHOD::failNoCert() const } +bool SSL_METHOD::multipleProtocol() const +{ + return multipleProtocol_; +} + + SSL_CTX::SSL_CTX(SSL_METHOD* meth) - : method_(meth), certificate_(0), privateKey_(0) + : method_(meth), certificate_(0), privateKey_(0), passwordCb_(0), + userData_(0) {} @@ -1558,7 +1713,7 @@ SSL_CTX::~SSL_CTX() ysDelete(certificate_); ysDelete(privateKey_); - mySTL::for_each(caList_.begin(), caList_.end(), del_ptr_zero()); + STL::for_each(caList_.begin(), caList_.end(), del_ptr_zero()); } @@ -1611,6 +1766,30 @@ const Stats& SSL_CTX::GetStats() const } +pem_password_cb SSL_CTX::GetPasswordCb() const +{ + return passwordCb_; +} + + +void SSL_CTX::SetPasswordCb(pem_password_cb cb) +{ + passwordCb_ = cb; +} + + +void* SSL_CTX::GetUserData() const +{ + return userData_; +} + + +void SSL_CTX::SetUserData(void* data) +{ + userData_ = data; +} + + void SSL_CTX::setVerifyPeer() { method_->setVerifyPeer(); @@ -1914,12 +2093,33 @@ Hashes& sslHashes::use_certVerify() } +Buffers::Buffers() : rawInput_(0) +{} + + Buffers::~Buffers() { - mySTL::for_each(handShakeList_.begin(), handShakeList_.end(), + STL::for_each(handShakeList_.begin(), handShakeList_.end(), del_ptr_zero()) ; - mySTL::for_each(dataList_.begin(), dataList_.end(), + STL::for_each(dataList_.begin(), dataList_.end(), del_ptr_zero()) ; + ysDelete(rawInput_); +} + + +void Buffers::SetRawInput(input_buffer* ib) +{ + assert(rawInput_ == 0); + rawInput_ = ib; +} + + +input_buffer* Buffers::TakeRawInput() +{ + input_buffer* ret = rawInput_; + rawInput_ = 0; + + return ret; } @@ -2026,12 +2226,18 @@ X509_NAME::~X509_NAME() } -char* X509_NAME::GetName() +const char* X509_NAME::GetName() const { return name_; } +size_t X509_NAME::GetLength() const +{ + return sz_; +} + + X509::X509(const char* i, size_t iSz, const char* s, size_t sSz, const char* b, int bSz, const char* a, int aSz) : issuer_(i, iSz), subject_(s, sSz), @@ -2114,10 +2320,12 @@ extern "C" void yaSSL_CleanUp() TaoCrypt::CleanUp(); yaSSL::ysDelete(yaSSL::sslFactoryInstance); yaSSL::ysDelete(yaSSL::sessionsInstance); + yaSSL::ysDelete(yaSSL::errorsInstance); // In case user calls more than once, prevent seg fault yaSSL::sslFactoryInstance = 0; yaSSL::sessionsInstance = 0; + yaSSL::errorsInstance = 0; } @@ -2126,6 +2334,7 @@ namespace mySTL { template yaSSL::yassl_int_cpp_local1::SumData for_each<mySTL::list<yaSSL::input_buffer*>::iterator, yaSSL::yassl_int_cpp_local1::SumData>(mySTL::list<yaSSL::input_buffer*>::iterator, mySTL::list<yaSSL::input_buffer*>::iterator, yaSSL::yassl_int_cpp_local1::SumData); template yaSSL::yassl_int_cpp_local1::SumBuffer for_each<mySTL::list<yaSSL::output_buffer*>::iterator, yaSSL::yassl_int_cpp_local1::SumBuffer>(mySTL::list<yaSSL::output_buffer*>::iterator, mySTL::list<yaSSL::output_buffer*>::iterator, yaSSL::yassl_int_cpp_local1::SumBuffer); template mySTL::list<yaSSL::SSL_SESSION*>::iterator find_if<mySTL::list<yaSSL::SSL_SESSION*>::iterator, yaSSL::yassl_int_cpp_local2::sess_match>(mySTL::list<yaSSL::SSL_SESSION*>::iterator, mySTL::list<yaSSL::SSL_SESSION*>::iterator, yaSSL::yassl_int_cpp_local2::sess_match); +template mySTL::list<yaSSL::ThreadError>::iterator find_if<mySTL::list<yaSSL::ThreadError>::iterator, yaSSL::yassl_int_cpp_local2::thr_match>(mySTL::list<yaSSL::ThreadError>::iterator, mySTL::list<yaSSL::ThreadError>::iterator, yaSSL::yassl_int_cpp_local2::thr_match); } #endif diff --git a/extra/yassl/taocrypt/CMakeLists.txt b/extra/yassl/taocrypt/CMakeLists.txt index 0af0a242e5d..540827954d0 100755 --- a/extra/yassl/taocrypt/CMakeLists.txt +++ b/extra/yassl/taocrypt/CMakeLists.txt @@ -1,4 +1,4 @@ -INCLUDE_DIRECTORIES(../mySTL include) +INCLUDE_DIRECTORIES(mySTL include) ADD_LIBRARY(taocrypt src/aes.cpp src/aestables.cpp src/algebra.cpp src/arc4.cpp src/asn.cpp src/coding.cpp src/des.cpp src/dh.cpp src/dsa.cpp src/file.cpp src/hash.cpp src/integer.cpp src/md2.cpp diff --git a/extra/yassl/taocrypt/COPYING b/extra/yassl/taocrypt/COPYING new file mode 100644 index 00000000000..d60c31a97a5 --- /dev/null +++ b/extra/yassl/taocrypt/COPYING @@ -0,0 +1,340 @@ + GNU GENERAL PUBLIC LICENSE + Version 2, June 1991 + + Copyright (C) 1989, 1991 Free Software Foundation, Inc. + 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + Everyone is permitted to copy and distribute verbatim copies + of this license document, but changing it is not allowed. + + Preamble + + The licenses for most software are designed to take away your +freedom to share and change it. By contrast, the GNU General Public +License is intended to guarantee your freedom to share and change free +software--to make sure the software is free for all its users. This +General Public License applies to most of the Free Software +Foundation's software and to any other program whose authors commit to +using it. (Some other Free Software Foundation software is covered by +the GNU Library General Public License instead.) You can apply it to +your programs, too. + + When we speak of free software, we are referring to freedom, not +price. Our General Public Licenses are designed to make sure that you +have the freedom to distribute copies of free software (and charge for +this service if you wish), that you receive source code or can get it +if you want it, that you can change the software or use pieces of it +in new free programs; and that you know you can do these things. + + To protect your rights, we need to make restrictions that forbid +anyone to deny you these rights or to ask you to surrender the rights. +These restrictions translate to certain responsibilities for you if you +distribute copies of the software, or if you modify it. + + For example, if you distribute copies of such a program, whether +gratis or for a fee, you must give the recipients all the rights that +you have. You must make sure that they, too, receive or can get the +source code. And you must show them these terms so they know their +rights. + + We protect your rights with two steps: (1) copyright the software, and +(2) offer you this license which gives you legal permission to copy, +distribute and/or modify the software. + + Also, for each author's protection and ours, we want to make certain +that everyone understands that there is no warranty for this free +software. If the software is modified by someone else and passed on, we +want its recipients to know that what they have is not the original, so +that any problems introduced by others will not reflect on the original +authors' reputations. + + Finally, any free program is threatened constantly by software +patents. We wish to avoid the danger that redistributors of a free +program will individually obtain patent licenses, in effect making the +program proprietary. To prevent this, we have made it clear that any +patent must be licensed for everyone's free use or not licensed at all. + + The precise terms and conditions for copying, distribution and +modification follow. + + GNU GENERAL PUBLIC LICENSE + TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION + + 0. This License applies to any program or other work which contains +a notice placed by the copyright holder saying it may be distributed +under the terms of this General Public License. The "Program", below, +refers to any such program or work, and a "work based on the Program" +means either the Program or any derivative work under copyright law: +that is to say, a work containing the Program or a portion of it, +either verbatim or with modifications and/or translated into another +language. (Hereinafter, translation is included without limitation in +the term "modification".) Each licensee is addressed as "you". + +Activities other than copying, distribution and modification are not +covered by this License; they are outside its scope. The act of +running the Program is not restricted, and the output from the Program +is covered only if its contents constitute a work based on the +Program (independent of having been made by running the Program). +Whether that is true depends on what the Program does. + + 1. You may copy and distribute verbatim copies of the Program's +source code as you receive it, in any medium, provided that you +conspicuously and appropriately publish on each copy an appropriate +copyright notice and disclaimer of warranty; keep intact all the +notices that refer to this License and to the absence of any warranty; +and give any other recipients of the Program a copy of this License +along with the Program. + +You may charge a fee for the physical act of transferring a copy, and +you may at your option offer warranty protection in exchange for a fee. + + 2. You may modify your copy or copies of the Program or any portion +of it, thus forming a work based on the Program, and copy and +distribute such modifications or work under the terms of Section 1 +above, provided that you also meet all of these conditions: + + a) You must cause the modified files to carry prominent notices + stating that you changed the files and the date of any change. + + b) You must cause any work that you distribute or publish, that in + whole or in part contains or is derived from the Program or any + part thereof, to be licensed as a whole at no charge to all third + parties under the terms of this License. + + c) If the modified program normally reads commands interactively + when run, you must cause it, when started running for such + interactive use in the most ordinary way, to print or display an + announcement including an appropriate copyright notice and a + notice that there is no warranty (or else, saying that you provide + a warranty) and that users may redistribute the program under + these conditions, and telling the user how to view a copy of this + License. (Exception: if the Program itself is interactive but + does not normally print such an announcement, your work based on + the Program is not required to print an announcement.) + +These requirements apply to the modified work as a whole. If +identifiable sections of that work are not derived from the Program, +and can be reasonably considered independent and separate works in +themselves, then this License, and its terms, do not apply to those +sections when you distribute them as separate works. But when you +distribute the same sections as part of a whole which is a work based +on the Program, the distribution of the whole must be on the terms of +this License, whose permissions for other licensees extend to the +entire whole, and thus to each and every part regardless of who wrote it. + +Thus, it is not the intent of this section to claim rights or contest +your rights to work written entirely by you; rather, the intent is to +exercise the right to control the distribution of derivative or +collective works based on the Program. + +In addition, mere aggregation of another work not based on the Program +with the Program (or with a work based on the Program) on a volume of +a storage or distribution medium does not bring the other work under +the scope of this License. + + 3. You may copy and distribute the Program (or a work based on it, +under Section 2) in object code or executable form under the terms of +Sections 1 and 2 above provided that you also do one of the following: + + a) Accompany it with the complete corresponding machine-readable + source code, which must be distributed under the terms of Sections + 1 and 2 above on a medium customarily used for software interchange; or, + + b) Accompany it with a written offer, valid for at least three + years, to give any third party, for a charge no more than your + cost of physically performing source distribution, a complete + machine-readable copy of the corresponding source code, to be + distributed under the terms of Sections 1 and 2 above on a medium + customarily used for software interchange; or, + + c) Accompany it with the information you received as to the offer + to distribute corresponding source code. (This alternative is + allowed only for noncommercial distribution and only if you + received the program in object code or executable form with such + an offer, in accord with Subsection b above.) + +The source code for a work means the preferred form of the work for +making modifications to it. For an executable work, complete source +code means all the source code for all modules it contains, plus any +associated interface definition files, plus the scripts used to +control compilation and installation of the executable. However, as a +special exception, the source code distributed need not include +anything that is normally distributed (in either source or binary +form) with the major components (compiler, kernel, and so on) of the +operating system on which the executable runs, unless that component +itself accompanies the executable. + +If distribution of executable or object code is made by offering +access to copy from a designated place, then offering equivalent +access to copy the source code from the same place counts as +distribution of the source code, even though third parties are not +compelled to copy the source along with the object code. + + 4. You may not copy, modify, sublicense, or distribute the Program +except as expressly provided under this License. Any attempt +otherwise to copy, modify, sublicense or distribute the Program is +void, and will automatically terminate your rights under this License. +However, parties who have received copies, or rights, from you under +this License will not have their licenses terminated so long as such +parties remain in full compliance. + + 5. You are not required to accept this License, since you have not +signed it. However, nothing else grants you permission to modify or +distribute the Program or its derivative works. These actions are +prohibited by law if you do not accept this License. Therefore, by +modifying or distributing the Program (or any work based on the +Program), you indicate your acceptance of this License to do so, and +all its terms and conditions for copying, distributing or modifying +the Program or works based on it. + + 6. Each time you redistribute the Program (or any work based on the +Program), the recipient automatically receives a license from the +original licensor to copy, distribute or modify the Program subject to +these terms and conditions. You may not impose any further +restrictions on the recipients' exercise of the rights granted herein. +You are not responsible for enforcing compliance by third parties to +this License. + + 7. If, as a consequence of a court judgment or allegation of patent +infringement or for any other reason (not limited to patent issues), +conditions are imposed on you (whether by court order, agreement or +otherwise) that contradict the conditions of this License, they do not +excuse you from the conditions of this License. If you cannot +distribute so as to satisfy simultaneously your obligations under this +License and any other pertinent obligations, then as a consequence you +may not distribute the Program at all. For example, if a patent +license would not permit royalty-free redistribution of the Program by +all those who receive copies directly or indirectly through you, then +the only way you could satisfy both it and this License would be to +refrain entirely from distribution of the Program. + +If any portion of this section is held invalid or unenforceable under +any particular circumstance, the balance of the section is intended to +apply and the section as a whole is intended to apply in other +circumstances. + +It is not the purpose of this section to induce you to infringe any +patents or other property right claims or to contest validity of any +such claims; this section has the sole purpose of protecting the +integrity of the free software distribution system, which is +implemented by public license practices. Many people have made +generous contributions to the wide range of software distributed +through that system in reliance on consistent application of that +system; it is up to the author/donor to decide if he or she is willing +to distribute software through any other system and a licensee cannot +impose that choice. + +This section is intended to make thoroughly clear what is believed to +be a consequence of the rest of this License. + + 8. If the distribution and/or use of the Program is restricted in +certain countries either by patents or by copyrighted interfaces, the +original copyright holder who places the Program under this License +may add an explicit geographical distribution limitation excluding +those countries, so that distribution is permitted only in or among +countries not thus excluded. In such case, this License incorporates +the limitation as if written in the body of this License. + + 9. The Free Software Foundation may publish revised and/or new versions +of the General Public License from time to time. Such new versions will +be similar in spirit to the present version, but may differ in detail to +address new problems or concerns. + +Each version is given a distinguishing version number. If the Program +specifies a version number of this License which applies to it and "any +later version", you have the option of following the terms and conditions +either of that version or of any later version published by the Free +Software Foundation. If the Program does not specify a version number of +this License, you may choose any version ever published by the Free Software +Foundation. + + 10. If you wish to incorporate parts of the Program into other free +programs whose distribution conditions are different, write to the author +to ask for permission. For software which is copyrighted by the Free +Software Foundation, write to the Free Software Foundation; we sometimes +make exceptions for this. Our decision will be guided by the two goals +of preserving the free status of all derivatives of our free software and +of promoting the sharing and reuse of software generally. + + NO WARRANTY + + 11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY +FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN +OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES +PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED +OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF +MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS +TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE +PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING, +REPAIR OR CORRECTION. + + 12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING +WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR +REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, +INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING +OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED +TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY +YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER +PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE +POSSIBILITY OF SUCH DAMAGES. + + END OF TERMS AND CONDITIONS + + How to Apply These Terms to Your New Programs + + If you develop a new program, and you want it to be of the greatest +possible use to the public, the best way to achieve this is to make it +free software which everyone can redistribute and change under these terms. + + To do so, attach the following notices to the program. It is safest +to attach them to the start of each source file to most effectively +convey the exclusion of warranty; and each file should have at least +the "copyright" line and a pointer to where the full notice is found. + + <one line to give the program's name and a brief idea of what it does.> + Copyright (C) <year> <name of author> + + 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 + + +Also add information on how to contact you by electronic and paper mail. + +If the program is interactive, make it output a short notice like this +when it starts in an interactive mode: + + Gnomovision version 69, Copyright (C) year name of author + Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'. + This is free software, and you are welcome to redistribute it + under certain conditions; type `show c' for details. + +The hypothetical commands `show w' and `show c' should show the appropriate +parts of the General Public License. Of course, the commands you use may +be called something other than `show w' and `show c'; they could even be +mouse-clicks or menu items--whatever suits your program. + +You should also get your employer (if you work as a programmer) or your +school, if any, to sign a "copyright disclaimer" for the program, if +necessary. Here is a sample; alter the names: + + Yoyodyne, Inc., hereby disclaims all copyright interest in the program + `Gnomovision' (which makes passes at compilers) written by James Hacker. + + <signature of Ty Coon>, 1 April 1989 + Ty Coon, President of Vice + +This General Public License does not permit incorporating your program into +proprietary programs. If your program is a subroutine library, you may +consider it more useful to permit linking proprietary applications with the +library. If this is what you want to do, use the GNU Library General +Public License instead of this License. diff --git a/extra/yassl/taocrypt/INSTALL b/extra/yassl/taocrypt/INSTALL new file mode 100644 index 00000000000..54caf7c190f --- /dev/null +++ b/extra/yassl/taocrypt/INSTALL @@ -0,0 +1,229 @@ +Copyright (C) 1994, 1995, 1996, 1999, 2000, 2001, 2002 Free Software +Foundation, Inc. + + This file is free documentation; the Free Software Foundation gives +unlimited permission to copy, distribute and modify it. + +Basic Installation +================== + + These are generic installation instructions. + + The `configure' shell script attempts to guess correct values for +various system-dependent variables used during compilation. It uses +those values to create a `Makefile' in each directory of the package. +It may also create one or more `.h' files containing system-dependent +definitions. Finally, it creates a shell script `config.status' that +you can run in the future to recreate the current configuration, and a +file `config.log' containing compiler output (useful mainly for +debugging `configure'). + + It can also use an optional file (typically called `config.cache' +and enabled with `--cache-file=config.cache' or simply `-C') that saves +the results of its tests to speed up reconfiguring. (Caching is +disabled by default to prevent problems with accidental use of stale +cache files.) + + If you need to do unusual things to compile the package, please try +to figure out how `configure' could check whether to do them, and mail +diffs or instructions to the address given in the `README' so they can +be considered for the next release. If you are using the cache, and at +some point `config.cache' contains results you don't want to keep, you +may remove or edit it. + + The file `configure.ac' (or `configure.in') is used to create +`configure' by a program called `autoconf'. You only need +`configure.ac' if you want to change it or regenerate `configure' using +a newer version of `autoconf'. + +The simplest way to compile this package is: + + 1. `cd' to the directory containing the package's source code and type + `./configure' to configure the package for your system. If you're + using `csh' on an old version of System V, you might need to type + `sh ./configure' instead to prevent `csh' from trying to execute + `configure' itself. + + Running `configure' takes awhile. While running, it prints some + messages telling which features it is checking for. + + 2. Type `make' to compile the package. + + 3. Optionally, type `make check' to run any self-tests that come with + the package. + + 4. Type `make install' to install the programs and any data files and + documentation. + + 5. You can remove the program binaries and object files from the + source code directory by typing `make clean'. To also remove the + files that `configure' created (so you can compile the package for + a different kind of computer), type `make distclean'. There is + also a `make maintainer-clean' target, but that is intended mainly + for the package's developers. If you use it, you may have to get + all sorts of other programs in order to regenerate files that came + with the distribution. + +Compilers and Options +===================== + + Some systems require unusual options for compilation or linking that +the `configure' script does not know about. Run `./configure --help' +for details on some of the pertinent environment variables. + + You can give `configure' initial values for configuration parameters +by setting variables in the command line or in the environment. Here +is an example: + + ./configure CC=c89 CFLAGS=-O2 LIBS=-lposix + + *Note Defining Variables::, for more details. + +Compiling For Multiple Architectures +==================================== + + You can compile the package for more than one kind of computer at the +same time, by placing the object files for each architecture in their +own directory. To do this, you must use a version of `make' that +supports the `VPATH' variable, such as GNU `make'. `cd' to the +directory where you want the object files and executables to go and run +the `configure' script. `configure' automatically checks for the +source code in the directory that `configure' is in and in `..'. + + If you have to use a `make' that does not support the `VPATH' +variable, you have to compile the package for one architecture at a +time in the source code directory. After you have installed the +package for one architecture, use `make distclean' before reconfiguring +for another architecture. + +Installation Names +================== + + By default, `make install' will install the package's files in +`/usr/local/bin', `/usr/local/man', etc. You can specify an +installation prefix other than `/usr/local' by giving `configure' the +option `--prefix=PATH'. + + You can specify separate installation prefixes for +architecture-specific files and architecture-independent files. If you +give `configure' the option `--exec-prefix=PATH', the package will use +PATH as the prefix for installing programs and libraries. +Documentation and other data files will still use the regular prefix. + + In addition, if you use an unusual directory layout you can give +options like `--bindir=PATH' to specify different values for particular +kinds of files. Run `configure --help' for a list of the directories +you can set and what kinds of files go in them. + + If the package supports it, you can cause programs to be installed +with an extra prefix or suffix on their names by giving `configure' the +option `--program-prefix=PREFIX' or `--program-suffix=SUFFIX'. + +Optional Features +================= + + Some packages pay attention to `--enable-FEATURE' options to +`configure', where FEATURE indicates an optional part of the package. +They may also pay attention to `--with-PACKAGE' options, where PACKAGE +is something like `gnu-as' or `x' (for the X Window System). The +`README' should mention any `--enable-' and `--with-' options that the +package recognizes. + + For packages that use the X Window System, `configure' can usually +find the X include and library files automatically, but if it doesn't, +you can use the `configure' options `--x-includes=DIR' and +`--x-libraries=DIR' to specify their locations. + +Specifying the System Type +========================== + + There may be some features `configure' cannot figure out +automatically, but needs to determine by the type of machine the package +will run on. Usually, assuming the package is built to be run on the +_same_ architectures, `configure' can figure that out, but if it prints +a message saying it cannot guess the machine type, give it the +`--build=TYPE' option. TYPE can either be a short name for the system +type, such as `sun4', or a canonical name which has the form: + + CPU-COMPANY-SYSTEM + +where SYSTEM can have one of these forms: + + OS KERNEL-OS + + See the file `config.sub' for the possible values of each field. If +`config.sub' isn't included in this package, then this package doesn't +need to know the machine type. + + If you are _building_ compiler tools for cross-compiling, you should +use the `--target=TYPE' option to select the type of system they will +produce code for. + + If you want to _use_ a cross compiler, that generates code for a +platform different from the build platform, you should specify the +"host" platform (i.e., that on which the generated programs will +eventually be run) with `--host=TYPE'. + +Sharing Defaults +================ + + If you want to set default values for `configure' scripts to share, +you can create a site shell script called `config.site' that gives +default values for variables like `CC', `cache_file', and `prefix'. +`configure' looks for `PREFIX/share/config.site' if it exists, then +`PREFIX/etc/config.site' if it exists. Or, you can set the +`CONFIG_SITE' environment variable to the location of the site script. +A warning: not all `configure' scripts look for a site script. + +Defining Variables +================== + + Variables not defined in a site shell script can be set in the +environment passed to `configure'. However, some packages may run +configure again during the build, and the customized values of these +variables may be lost. In order to avoid this problem, you should set +them in the `configure' command line, using `VAR=value'. For example: + + ./configure CC=/usr/local2/bin/gcc + +will cause the specified gcc to be used as the C compiler (unless it is +overridden in the site shell script). + +`configure' Invocation +====================== + + `configure' recognizes the following options to control how it +operates. + +`--help' +`-h' + Print a summary of the options to `configure', and exit. + +`--version' +`-V' + Print the version of Autoconf used to generate the `configure' + script, and exit. + +`--cache-file=FILE' + Enable the cache: use and save the results of the tests in FILE, + traditionally `config.cache'. FILE defaults to `/dev/null' to + disable caching. + +`--config-cache' +`-C' + Alias for `--cache-file=config.cache'. + +`--quiet' +`--silent' +`-q' + Do not print messages saying which checks are being made. To + suppress all normal output, redirect it to `/dev/null' (any error + messages will still be shown). + +`--srcdir=DIR' + Look for the package's source code in directory DIR. Usually + `configure' can determine that directory automatically. + +`configure' also accepts some other, not widely useful, options. Run +`configure --help' for more details. + diff --git a/extra/yassl/taocrypt/Makefile.am b/extra/yassl/taocrypt/Makefile.am index e232b499cc7..f1340b38437 100644 --- a/extra/yassl/taocrypt/Makefile.am +++ b/extra/yassl/taocrypt/Makefile.am @@ -1,2 +1,2 @@ SUBDIRS = src test benchmark -EXTRA_DIST = taocrypt.dsw taocrypt.dsp CMakeLists.txt +EXTRA_DIST = taocrypt.dsw taocrypt.dsp CMakeLists.txt $(wildcard mySTL/*.hpp) diff --git a/extra/yassl/taocrypt/README b/extra/yassl/taocrypt/README new file mode 100644 index 00000000000..34e1744492e --- /dev/null +++ b/extra/yassl/taocrypt/README @@ -0,0 +1,37 @@ +TaoCrypt release 0.9.0 09/18/2006 + +This is the first release of TaoCrypt, it was previously only included with +yaSSL. TaoCrypt is highly portable and fast, its features include: + +One way hash functions: SHA-1, MD2, MD4, MD5, RIPEMD-160 +Message authentication codes: HMAC +Block Ciphers: DES, Triple-DES, AES, Blowfish, Twofish +Stream Ciphers: ARC4 +Public Key Crypto: RSA, DSA, Diffie-Hellman +Password based key derivation: PBKDF2 from PKCS #5 +Pseudo Random Number Generators +Lare Integer Support +Base 16/64 encoding/decoding +DER encoding/decoding +X.509 processing +SSE2 and ia32 asm for the right processors and compilers + + +To build on Unix + + ./configure + make + + To test the build, from the ./test directory run ./test + + +On Windows + + Open the taocrypt project workspace + Choose (Re)Build All + + To test the build, run the test executable + + +Please send any questions or comments to todd@yassl.com. + diff --git a/extra/yassl/taocrypt/benchmark/Makefile.am b/extra/yassl/taocrypt/benchmark/Makefile.am index 81200ff7e6a..a5b1713427c 100644 --- a/extra/yassl/taocrypt/benchmark/Makefile.am +++ b/extra/yassl/taocrypt/benchmark/Makefile.am @@ -1,8 +1,6 @@ -INCLUDES = -I../include -I../../mySTL +INCLUDES = -I../include -I../mySTL bin_PROGRAMS = benchmark benchmark_SOURCES = benchmark.cpp -benchmark_LDFLAGS = -L../src -benchmark_LDADD = -ltaocrypt +benchmark_LDADD = $(top_builddir)/extra/yassl/taocrypt/src/libtaocrypt.la benchmark_CXXFLAGS = -DYASSL_PURE_C -benchmark_DEPENDENCIES = ../src/libtaocrypt.la EXTRA_DIST = benchmark.dsp rsa1024.der dh1024.der dsa1024.der make.bat diff --git a/extra/yassl/taocrypt/include/asn.hpp b/extra/yassl/taocrypt/include/asn.hpp index 8bea2ae780b..dbee54be6f1 100644 --- a/extra/yassl/taocrypt/include/asn.hpp +++ b/extra/yassl/taocrypt/include/asn.hpp @@ -33,10 +33,12 @@ #include "misc.hpp" #include "block.hpp" -#include "list.hpp" #include "error.hpp" +#include STL_LIST_FILE +namespace STL = STL_NAMESPACE; + namespace TaoCrypt { @@ -232,7 +234,7 @@ private: }; -typedef mySTL::list<Signer*> SignerList; +typedef STL::list<Signer*> SignerList; enum SigType { SHAwDSA = 517, MD2wRSA = 646, MD5wRSA = 648, SHAwRSA =649}; diff --git a/extra/yassl/taocrypt/include/block.hpp b/extra/yassl/taocrypt/include/block.hpp index 88cb06f62f1..a931158a83d 100644 --- a/extra/yassl/taocrypt/include/block.hpp +++ b/extra/yassl/taocrypt/include/block.hpp @@ -31,12 +31,14 @@ #ifndef TAO_CRYPT_BLOCK_HPP #define TAO_CRYPT_BLOCK_HPP -#include "algorithm.hpp" // mySTL::swap #include "misc.hpp" #include <string.h> // memcpy #include <stddef.h> // ptrdiff_t +#include STL_ALGORITHM_FILE +namespace STL = STL_NAMESPACE; + namespace TaoCrypt { @@ -80,7 +82,7 @@ typename A::pointer StdReallocate(A& a, T* p, typename A::size_type oldSize, typename A::pointer newPointer = b.allocate(newSize, 0); memcpy(newPointer, p, sizeof(T) * min(oldSize, newSize)); a.deallocate(p, oldSize); - mySTL::swap(a, b); + STL::swap(a, b); return newPointer; } else { @@ -183,9 +185,9 @@ public: } void Swap(Block& other) { - mySTL::swap(sz_, other.sz_); - mySTL::swap(buffer_, other.buffer_); - mySTL::swap(allocator_, other.allocator_); + STL::swap(sz_, other.sz_); + STL::swap(buffer_, other.buffer_); + STL::swap(allocator_, other.allocator_); } ~Block() { allocator_.deallocate(buffer_, sz_); } diff --git a/extra/yassl/taocrypt/include/blowfish.hpp b/extra/yassl/taocrypt/include/blowfish.hpp index fbc4f223702..40953624232 100644 --- a/extra/yassl/taocrypt/include/blowfish.hpp +++ b/extra/yassl/taocrypt/include/blowfish.hpp @@ -32,7 +32,11 @@ #include "misc.hpp" #include "modes.hpp" -#include "algorithm.hpp" +#include STL_ALGORITHM_FILE + + +namespace STL = STL_NAMESPACE; + namespace TaoCrypt { diff --git a/extra/yassl/taocrypt/include/error.hpp b/extra/yassl/taocrypt/include/error.hpp index b0ff9b280ba..1a93056db45 100644 --- a/extra/yassl/taocrypt/include/error.hpp +++ b/extra/yassl/taocrypt/include/error.hpp @@ -37,7 +37,7 @@ namespace TaoCrypt { enum ErrorNumber { -NO_ERROR = 0, // "not in error state" +NO_ERROR_E = 0, // "not in error state" // RandomNumberGenerator WINCRYPT_E = 1001, // "bad wincrypt acquire" @@ -78,7 +78,7 @@ SIG_OTHER_E = 1039 // "bad other signature confirmation" struct Error { ErrorNumber what_; // description number, 0 for no error - explicit Error(ErrorNumber w = NO_ERROR) : what_(w) {} + explicit Error(ErrorNumber w = NO_ERROR_E) : what_(w) {} ErrorNumber What() const { return what_; } void SetError(ErrorNumber w) { what_ = w; } diff --git a/extra/yassl/taocrypt/include/file.hpp b/extra/yassl/taocrypt/include/file.hpp index 87fc6139f8f..c12b5c73bac 100644 --- a/extra/yassl/taocrypt/include/file.hpp +++ b/extra/yassl/taocrypt/include/file.hpp @@ -83,7 +83,7 @@ private: void Swap(Source& other) { buffer_.Swap(other.buffer_); - mySTL::swap(current_, other.current_); + STL::swap(current_, other.current_); } }; diff --git a/extra/yassl/taocrypt/include/integer.hpp b/extra/yassl/taocrypt/include/integer.hpp index 7e4f6450316..70b4dc79e73 100644 --- a/extra/yassl/taocrypt/include/integer.hpp +++ b/extra/yassl/taocrypt/include/integer.hpp @@ -44,8 +44,8 @@ #include "block.hpp" #include "random.hpp" #include "file.hpp" -#include "algorithm.hpp" // mySTL::swap #include <string.h> +#include STL_ALGORITHM_FILE #ifdef TAOCRYPT_X86ASM_AVAILABLE diff --git a/extra/yassl/taocrypt/include/misc.hpp b/extra/yassl/taocrypt/include/misc.hpp index 48604620706..3d2d4c62466 100644 --- a/extra/yassl/taocrypt/include/misc.hpp +++ b/extra/yassl/taocrypt/include/misc.hpp @@ -198,6 +198,23 @@ void CleanUp(); #endif +#ifdef USE_SYS_STL + // use system STL + #define STL_VECTOR_FILE <vector> + #define STL_LIST_FILE <list> + #define STL_ALGORITHM_FILE <algorithm> + #define STL_MEMORY_FILE <memory> + #define STL_NAMESPACE std +#else + // use mySTL + #define STL_VECTOR_FILE "vector.hpp" + #define STL_LIST_FILE "list.hpp" + #define STL_ALGORITHM_FILE "algorithm.hpp" + #define STL_MEMORY_FILE "memory.hpp" + #define STL_NAMESPACE mySTL +#endif + + // ***************** DLL related ******************** #ifdef TAOCRYPT_WIN32_AVAILABLE diff --git a/extra/yassl/taocrypt/include/pwdbased.hpp b/extra/yassl/taocrypt/include/pwdbased.hpp index c3e916e3d83..78df7ede02e 100644 --- a/extra/yassl/taocrypt/include/pwdbased.hpp +++ b/extra/yassl/taocrypt/include/pwdbased.hpp @@ -74,7 +74,7 @@ word32 PBKDF2_HMAC<T>::DeriveKey(byte* derived, word32 dLen, const byte* pwd, } hmac.Final(buffer.get_buffer()); - word32 segmentLen = mySTL::min(dLen, buffer.size()); + word32 segmentLen = min(dLen, buffer.size()); memcpy(derived, buffer.get_buffer(), segmentLen); for (j = 1; j < iterations; j++) { diff --git a/extra/yassl/taocrypt/include/twofish.hpp b/extra/yassl/taocrypt/include/twofish.hpp index 0529c37d6c5..ba144d2defb 100644 --- a/extra/yassl/taocrypt/include/twofish.hpp +++ b/extra/yassl/taocrypt/include/twofish.hpp @@ -32,7 +32,11 @@ #include "misc.hpp" #include "modes.hpp" -#include "algorithm.hpp" +#include STL_ALGORITHM_FILE + + +namespace STL = STL_NAMESPACE; + namespace TaoCrypt { diff --git a/extra/yassl/mySTL/algorithm.hpp b/extra/yassl/taocrypt/mySTL/algorithm.hpp index efc7aa21a07..9a51d1f2281 100644 --- a/extra/yassl/mySTL/algorithm.hpp +++ b/extra/yassl/taocrypt/mySTL/algorithm.hpp @@ -8,7 +8,7 @@ * 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. - * + * * There are special exceptions to the terms and conditions of the GPL as it * is applied to yaSSL. View the full text of the exception in the file * FLOSS-EXCEPTIONS in the directory of this software distribution. diff --git a/extra/yassl/mySTL/helpers.hpp b/extra/yassl/taocrypt/mySTL/helpers.hpp index c4449519db3..43381c0f6ea 100644 --- a/extra/yassl/mySTL/helpers.hpp +++ b/extra/yassl/taocrypt/mySTL/helpers.hpp @@ -113,6 +113,47 @@ PlaceIter uninit_fill_n(PlaceIter place, Size n, const T& value) } +template <typename T> +T* GetArrayMemory(size_t items) +{ + unsigned char* ret; + + #ifdef YASSL_LIB + ret = NEW_YS unsigned char[sizeof(T) * items]; + #else + ret = NEW_TC unsigned char[sizeof(T) * items]; + #endif + + return reinterpret_cast<T*>(ret); +} + + +template <typename T> +void FreeArrayMemory(T* ptr) +{ + unsigned char* p = reinterpret_cast<unsigned char*>(ptr); + + #ifdef YASSL_LIB + yaSSL::ysArrayDelete(p); + #else + TaoCrypt::tcArrayDelete(p); + #endif +} + + + +inline void* GetMemory(size_t bytes) +{ + return GetArrayMemory<unsigned char>(bytes); +} + + +inline void FreeMemory(void* ptr) +{ + FreeArrayMemory(ptr); +} + + } // namespace mySTL diff --git a/extra/yassl/mySTL/list.hpp b/extra/yassl/taocrypt/mySTL/list.hpp index 11a1a914868..831c5bbbbbd 100644 --- a/extra/yassl/mySTL/list.hpp +++ b/extra/yassl/taocrypt/mySTL/list.hpp @@ -33,7 +33,6 @@ #include "helpers.hpp" -#include <stdlib.h> namespace mySTL { @@ -75,8 +74,7 @@ public: class iterator { node* current_; public: - iterator() : current_(0) {} - explicit iterator(node* p) : current_(p) {} + explicit iterator(node* p = 0) : current_(p) {} T& operator*() const { @@ -127,11 +125,67 @@ public: friend class list<T>; }; + + class reverse_iterator { + node* current_; + public: + explicit reverse_iterator(node* p = 0) : current_(p) {} + + T& operator*() const + { + return current_->value_; + } + + T* operator->() const + { + return &(operator*()); + } + + reverse_iterator& operator++() + { + current_ = current_->prev_; + return *this; + } + + reverse_iterator& operator--() + { + current_ = current_->next_; + return *this; + } + + reverse_iterator operator++(int) + { + reverse_iterator tmp = *this; + current_ = current_->prev_; + return tmp; + } + + reverse_iterator operator--(int) + { + reverse_iterator tmp = *this; + current_ = current_->next_; + return tmp; + } + + bool operator==(const reverse_iterator& other) const + { + return current_ == other.current_; + } + + bool operator!=(const reverse_iterator& other) const + { + return current_ != other.current_; + } + + friend class list<T>; + }; + bool erase(iterator); - iterator begin() const { return iterator(head_); } - iterator rbegin() const { return iterator(tail_); } - iterator end() const { return iterator(); } + iterator begin() const { return iterator(head_); } + reverse_iterator rbegin() const { return reverse_iterator(tail_); } + iterator end() const { return iterator(); } + reverse_iterator rend() const { return reverse_iterator(); } typedef iterator const_iterator; // for now @@ -158,7 +212,7 @@ list<T>::~list() for (; start; start = next_) { next_ = start->next_; destroy(start); - free(start); + FreeMemory(start); } } @@ -166,8 +220,7 @@ list<T>::~list() template<typename T> void list<T>::push_front(T t) { - void* mem = malloc(sizeof(node)); - if (!mem) abort(); + void* mem = GetMemory(sizeof(node)); node* add = new (reinterpret_cast<yassl_pointer>(mem)) node(t); if (head_) { @@ -196,7 +249,7 @@ void list<T>::pop_front() head_->prev_ = 0; } destroy(front); - free(front); + FreeMemory(front); --sz_; } @@ -204,7 +257,7 @@ void list<T>::pop_front() template<typename T> T list<T>::front() const { - if (head_ == 0) return 0; + if (head_ == 0) return T(); return head_->value_; } @@ -212,8 +265,7 @@ T list<T>::front() const template<typename T> void list<T>::push_back(T t) { - void* mem = malloc(sizeof(node)); - if (!mem) abort(); + void* mem = GetMemory(sizeof(node)); node* add = new (reinterpret_cast<yassl_pointer>(mem)) node(t); if (tail_) { @@ -242,7 +294,7 @@ void list<T>::pop_back() tail_->next_ = 0; } destroy(rear); - free(rear); + FreeMemory(rear); --sz_; } @@ -250,7 +302,7 @@ void list<T>::pop_back() template<typename T> T list<T>::back() const { - if (tail_ == 0) return 0; + if (tail_ == 0) return T(); return tail_->value_; } @@ -286,7 +338,7 @@ bool list<T>::remove(T t) del->next_->prev_ = del->prev_; destroy(del); - free(del); + FreeMemory(del); --sz_; } return true; @@ -309,78 +361,13 @@ bool list<T>::erase(iterator iter) del->next_->prev_ = del->prev_; destroy(del); - free(del); + FreeMemory(del); --sz_; } return true; } -/* MSVC can't handle ?? - -template<typename T> -T& list<T>::iterator::operator*() const -{ - return current_->value_; -} - - -template<typename T> -T* list<T>::iterator::operator->() const -{ - return &(operator*()); -} - - -template<typename T> -typename list<T>::iterator& list<T>::iterator::operator++() -{ - current_ = current_->next_; - return *this; -} - - -template<typename T> -typename list<T>::iterator& list<T>::iterator::operator--() -{ - current_ = current_->prev_; - return *this; -} - - -template<typename T> -typename list<T>::iterator& list<T>::iterator::operator++(int) -{ - iterator tmp = *this; - current_ = current_->next_; - return tmp; -} - - -template<typename T> -typename list<T>::iterator& list<T>::iterator::operator--(int) -{ - iterator tmp = *this; - current_ = current_->prev_; - return tmp; -} - - -template<typename T> -bool list<T>::iterator::operator==(const iterator& other) const -{ - return current_ == other.current_; -} - - -template<typename T> -bool list<T>::iterator::operator!=(const iterator& other) const -{ - return current_ != other.current_; -} -*/ // end MSVC 6 can't handle - - } // namespace mySTL diff --git a/extra/yassl/mySTL/memory.hpp b/extra/yassl/taocrypt/mySTL/memory.hpp index f480af12316..5855423c6fc 100644 --- a/extra/yassl/mySTL/memory.hpp +++ b/extra/yassl/taocrypt/mySTL/memory.hpp @@ -31,6 +31,7 @@ #ifndef mySTL_MEMORY_HPP #define mySTL_MEMORY_HPP +#include "memory_array.hpp" // for auto_array #ifdef _MSC_VER // disable operator-> warning for builtins @@ -43,27 +44,25 @@ namespace mySTL { template<typename T> struct auto_ptr_ref { - typedef void (*Deletor)(T*); - T* ptr_; - Deletor del_; - auto_ptr_ref(T* p, Deletor d) : ptr_(p), del_(d) {} + T* ptr_; + explicit auto_ptr_ref(T* p) : ptr_(p) {} }; template<typename T> class auto_ptr { - typedef void (*Deletor)(T*); T* ptr_; - Deletor del_; void Destroy() { - del_(ptr_); + #ifdef YASSL_LIB + yaSSL::ysDelete(ptr_); + #else + TaoCrypt::tcDelete(ptr_); + #endif } public: - auto_ptr(T* p, Deletor d) : ptr_(p), del_(d) {} - - explicit auto_ptr(Deletor d) : ptr_(0), del_(d) {} + explicit auto_ptr(T* p = 0) : ptr_(p) {} ~auto_ptr() { @@ -71,14 +70,13 @@ public: } - auto_ptr(auto_ptr& other) : ptr_(other.release()), del_(other.del_) {} + auto_ptr(auto_ptr& other) : ptr_(other.release()) {} auto_ptr& operator=(auto_ptr& that) { if (this != &that) { Destroy(); ptr_ = that.release(); - del_ = that.del_; } return *this; } @@ -115,14 +113,13 @@ public: } // auto_ptr_ref conversions - auto_ptr(auto_ptr_ref<T> ref) : ptr_(ref.ptr_), del_(ref.del_) {} + auto_ptr(auto_ptr_ref<T> ref) : ptr_(ref.ptr_) {} auto_ptr& operator=(auto_ptr_ref<T> ref) { if (this->ptr_ != ref.ptr_) { Destroy(); ptr_ = ref.ptr_; - del_ = ref.del_; } return *this; } @@ -130,13 +127,13 @@ public: template<typename T2> operator auto_ptr<T2>() { - return auto_ptr<T2>(this->release(), this->del_); + return auto_ptr<T2>(this->release()); } template<typename T2> operator auto_ptr_ref<T2>() { - return auto_ptr_ref<T2>(this->release(), this->del_); + return auto_ptr_ref<T2>(this->release()); } }; diff --git a/extra/yassl/taocrypt/mySTL/memory_array.hpp b/extra/yassl/taocrypt/mySTL/memory_array.hpp new file mode 100644 index 00000000000..f089c69f815 --- /dev/null +++ b/extra/yassl/taocrypt/mySTL/memory_array.hpp @@ -0,0 +1,142 @@ +/* mySTL memory_array.hpp + * + * Copyright (C) 2003 Sawtooth Consulting Ltd. + * + * This file is part of yaSSL. + * + * yaSSL 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. + * + * There are special exceptions to the terms and conditions of the GPL as it + * is applied to yaSSL. View the full text of the exception in the file + * FLOSS-EXCEPTIONS in the directory of this software distribution. + * + * yaSSL 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 + */ + + +/* mySTL memory_arry implements auto_array + * + */ + +#ifndef mySTL_MEMORY_ARRAY_HPP +#define mySTL_MEMORY_ARRAY_HPP + + +#ifdef _MSC_VER + // disable operator-> warning for builtins + #pragma warning(disable:4284) +#endif + + +namespace mySTL { + + +template<typename T> +struct auto_array_ref { + T* ptr_; + explicit auto_array_ref(T* p) : ptr_(p) {} +}; + + +template<typename T> +class auto_array { + T* ptr_; + + void Destroy() + { + #ifdef YASSL_LIB + yaSSL::ysArrayDelete(ptr_); + #else + TaoCrypt::tcArrayDelete(ptr_); + #endif + } +public: + explicit auto_array(T* p = 0) : ptr_(p) {} + + ~auto_array() + { + Destroy(); + } + + + auto_array(auto_array& other) : ptr_(other.release()) {} + + auto_array& operator=(auto_array& that) + { + if (this != &that) { + Destroy(); + ptr_ = that.release(); + } + return *this; + } + + + T* operator->() const + { + return ptr_; + } + + T& operator*() const + { + return *ptr_; + } + + T* get() const + { + return ptr_; + } + + T* release() + { + T* tmp = ptr_; + ptr_ = 0; + return tmp; + } + + void reset(T* p = 0) + { + if (ptr_ != p) { + Destroy(); + ptr_ = p; + } + } + + // auto_array_ref conversions + auto_array(auto_array_ref<T> ref) : ptr_(ref.ptr_) {} + + auto_array& operator=(auto_array_ref<T> ref) + { + if (this->ptr_ != ref.ptr_) { + Destroy(); + ptr_ = ref.ptr_; + } + return *this; + } + + template<typename T2> + operator auto_array<T2>() + { + return auto_array<T2>(this->release()); + } + + template<typename T2> + operator auto_array_ref<T2>() + { + return auto_array_ref<T2>(this->release()); + } +}; + + +} // namespace mySTL + +#endif // mySTL_MEMORY_ARRAY_HPP diff --git a/extra/yassl/mySTL/pair.hpp b/extra/yassl/taocrypt/mySTL/pair.hpp index 13916fece13..13916fece13 100644 --- a/extra/yassl/mySTL/pair.hpp +++ b/extra/yassl/taocrypt/mySTL/pair.hpp diff --git a/extra/yassl/mySTL/stdexcept.hpp b/extra/yassl/taocrypt/mySTL/stdexcept.hpp index 4fd343ae6fd..4fd343ae6fd 100644 --- a/extra/yassl/mySTL/stdexcept.hpp +++ b/extra/yassl/taocrypt/mySTL/stdexcept.hpp diff --git a/extra/yassl/mySTL/vector.hpp b/extra/yassl/taocrypt/mySTL/vector.hpp index 6a412447b91..902e014f75b 100644 --- a/extra/yassl/mySTL/vector.hpp +++ b/extra/yassl/taocrypt/mySTL/vector.hpp @@ -34,7 +34,6 @@ #include "helpers.hpp" // construct, destory, fill, etc. #include "algorithm.hpp" // swap #include <assert.h> // assert -#include <stdlib.h> // malloc namespace mySTL { @@ -49,14 +48,15 @@ struct vector_base { vector_base() : start_(0), finish_(0), end_of_storage_(0) {} vector_base(size_t n) { - // Don't allow malloc(0), if n is 0 use 1 - start_ = static_cast<T*>(malloc((n ? n : 1) * sizeof(T))); - if (!start_) abort(); + start_ = GetArrayMemory<T>(n); finish_ = start_; end_of_storage_ = start_ + n; } - ~vector_base() { if (start_) free(start_); } + ~vector_base() + { + FreeArrayMemory(start_); + } void Swap(vector_base& that) { @@ -71,6 +71,9 @@ struct vector_base { template <typename T> class vector { public: + typedef T* iterator; + typedef const T* const_iterator; + vector() {} explicit vector(size_t n) : vec_(n) { diff --git a/extra/yassl/taocrypt/src/Makefile.am b/extra/yassl/taocrypt/src/Makefile.am index 1110ed335b8..6d02a625275 100644 --- a/extra/yassl/taocrypt/src/Makefile.am +++ b/extra/yassl/taocrypt/src/Makefile.am @@ -1,4 +1,4 @@ -INCLUDES = -I../include -I../../mySTL +INCLUDES = -I../include -I../mySTL noinst_LTLIBRARIES = libtaocrypt.la @@ -11,3 +11,7 @@ libtaocrypt_la_SOURCES = aes.cpp aestables.cpp algebra.cpp arc4.cpp \ libtaocrypt_la_CXXFLAGS = @yassl_taocrypt_extra_cxxflags@ -DYASSL_PURE_C EXTRA_DIST = $(wildcard ../include/*.hpp) + +# Don't update the files from bitkeeper +%::SCCS/s.% + diff --git a/extra/yassl/taocrypt/src/algebra.cpp b/extra/yassl/taocrypt/src/algebra.cpp index e9bc3fceac0..375cd6cd524 100644 --- a/extra/yassl/taocrypt/src/algebra.cpp +++ b/extra/yassl/taocrypt/src/algebra.cpp @@ -29,7 +29,10 @@ #include "runtime.hpp" #include "algebra.hpp" -#include "vector.hpp" // mySTL::vector (simple) +#include STL_VECTOR_FILE + + +namespace STL = STL_NAMESPACE; namespace TaoCrypt { @@ -82,7 +85,7 @@ const Integer& AbstractEuclideanDomain::Mod(const Element &a, const Integer& AbstractEuclideanDomain::Gcd(const Element &a, const Element &b) const { - mySTL::vector<Element> g(3); + STL::vector<Element> g(3); g[0]= b; g[1]= a; unsigned int i0=0, i1=1, i2=2; @@ -115,7 +118,7 @@ Integer AbstractGroup::CascadeScalarMultiply(const Element &x, const unsigned w = (expLen <= 46 ? 1 : (expLen <= 260 ? 2 : 3)); const unsigned tableSize = 1<<w; - mySTL::vector<Element> powerTable(tableSize << w); + STL::vector<Element> powerTable(tableSize << w); powerTable[1] = x; powerTable[tableSize] = y; @@ -240,8 +243,8 @@ struct WindowSlider void AbstractGroup::SimultaneousMultiply(Integer *results, const Integer &base, const Integer *expBegin, unsigned int expCount) const { - mySTL::vector<mySTL::vector<Element> > buckets(expCount); - mySTL::vector<WindowSlider> exponents; + STL::vector<STL::vector<Element> > buckets(expCount); + STL::vector<WindowSlider> exponents; exponents.reserve(expCount); unsigned int i; @@ -332,6 +335,8 @@ void AbstractRing::SimultaneousExponentiate(Integer *results, namespace mySTL { template TaoCrypt::WindowSlider* uninit_copy<TaoCrypt::WindowSlider*, TaoCrypt::WindowSlider*>(TaoCrypt::WindowSlider*, TaoCrypt::WindowSlider*, TaoCrypt::WindowSlider*); template void destroy<TaoCrypt::WindowSlider*>(TaoCrypt::WindowSlider*, TaoCrypt::WindowSlider*); +template TaoCrypt::WindowSlider* GetArrayMemory<TaoCrypt::WindowSlider>(size_t); +template void FreeArrayMemory<TaoCrypt::WindowSlider>(TaoCrypt::WindowSlider*); } #endif diff --git a/extra/yassl/taocrypt/src/asn.cpp b/extra/yassl/taocrypt/src/asn.cpp index 45fb1e60a0c..3dc3638d85f 100644 --- a/extra/yassl/taocrypt/src/asn.cpp +++ b/extra/yassl/taocrypt/src/asn.cpp @@ -38,7 +38,8 @@ #include "sha.hpp" #include "coding.hpp" #include <time.h> // gmtime(); -#include "memory.hpp" // mySTL::auto_ptr +#include "memory.hpp" // some auto_ptr don't have reset, also need auto_array + namespace TaoCrypt { @@ -202,13 +203,13 @@ void PublicKey::SetKey(const byte* k) void PublicKey::AddToEnd(const byte* data, word32 len) { - mySTL::auto_ptr<byte> tmp(NEW_TC byte[sz_ + len], tcArrayDelete); + mySTL::auto_array<byte> tmp(NEW_TC byte[sz_ + len]); memcpy(tmp.get(), key_, sz_); memcpy(tmp.get() + sz_, data, len); byte* del = 0; - mySTL::swap(del, key_); + STL::swap(del, key_); tcArrayDelete(del); key_ = tmp.release(); @@ -856,7 +857,7 @@ bool CertDecoder::ValidateSignature(SignerList* signers) bool CertDecoder::ConfirmSignature(Source& pub) { HashType ht; - mySTL::auto_ptr<HASH> hasher(tcDelete); + mySTL::auto_ptr<HASH> hasher; if (signatureOID_ == MD5wRSA) { hasher.reset(NEW_TC MD5); diff --git a/extra/yassl/taocrypt/src/blowfish.cpp b/extra/yassl/taocrypt/src/blowfish.cpp index cc929cd7d41..40ae1a17e6c 100644 --- a/extra/yassl/taocrypt/src/blowfish.cpp +++ b/extra/yassl/taocrypt/src/blowfish.cpp @@ -133,7 +133,7 @@ void Blowfish::SetKey(const byte* key_string, word32 keylength, CipherDir dir) if (dir==DECRYPTION) for (i=0; i<(ROUNDS+2)/2; i++) - mySTL::swap(pbox_[i], pbox_[ROUNDS+1-i]); + STL::swap(pbox_[i], pbox_[ROUNDS+1-i]); } diff --git a/extra/yassl/taocrypt/src/crypto.cpp b/extra/yassl/taocrypt/src/crypto.cpp new file mode 100644 index 00000000000..95238100f5d --- /dev/null +++ b/extra/yassl/taocrypt/src/crypto.cpp @@ -0,0 +1,39 @@ +/* crypto.cpp + * + * Copyright (C) 2003 Sawtooth Consulting Ltd. + * + * This file is part of yaSSL. + * + * yaSSL 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. + * + * There are special exceptions to the terms and conditions of the GPL as it + * is applied to yaSSL. View the full text of the exception in the file + * FLOSS-EXCEPTIONS in the directory of this software distribution. + * + * yaSSL 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 + */ + +/* put features that other apps expect from OpenSSL type crypto */ + + + +extern "C" { + + // for libcurl configure test, these are the signatures they use + // locking handled internally by library + char CRYPTO_lock() { return 0;} + char CRYPTO_add_lock() { return 0;} +} // extern "C" + + + diff --git a/extra/yassl/taocrypt/src/des.cpp b/extra/yassl/taocrypt/src/des.cpp index 054c8c2eb78..2628e142bae 100644 --- a/extra/yassl/taocrypt/src/des.cpp +++ b/extra/yassl/taocrypt/src/des.cpp @@ -34,7 +34,10 @@ #include "runtime.hpp" #include "des.hpp" -#include "algorithm.hpp" // mySTL::swap +#include STL_ALGORITHM_FILE + + +namespace STL = STL_NAMESPACE; #if defined(TAOCRYPT_X86ASM_AVAILABLE) && defined(TAO_ASM) @@ -265,8 +268,8 @@ void BasicDES::SetKey(const byte* key, word32 /*length*/, CipherDir dir) // reverse key schedule order if (dir == DECRYPTION) for (i = 0; i < 16; i += 2) { - mySTL::swap(k_[i], k_[32 - 2 - i]); - mySTL::swap(k_[i+1], k_[32 - 1 - i]); + STL::swap(k_[i], k_[32 - 2 - i]); + STL::swap(k_[i+1], k_[32 - 1 - i]); } } diff --git a/extra/yassl/taocrypt/src/dh.cpp b/extra/yassl/taocrypt/src/dh.cpp index aec7122b70b..671a20d0d78 100644 --- a/extra/yassl/taocrypt/src/dh.cpp +++ b/extra/yassl/taocrypt/src/dh.cpp @@ -61,7 +61,7 @@ void DH::GenerateKeyPair(RandomNumberGenerator& rng, byte* priv, byte* pub) // Generate private value void DH::GeneratePrivate(RandomNumberGenerator& rng, byte* priv) { - Integer x(rng, Integer::One(), mySTL::min(p_ - 1, + Integer x(rng, Integer::One(), min(p_ - 1, Integer::Power2(2*DiscreteLogWorkFactor(p_.BitCount())) ) ); x.Encode(priv, p_.ByteCount()); } diff --git a/extra/yassl/taocrypt/src/integer.cpp b/extra/yassl/taocrypt/src/integer.cpp index 823c0c5e193..500160cfe37 100644 --- a/extra/yassl/taocrypt/src/integer.cpp +++ b/extra/yassl/taocrypt/src/integer.cpp @@ -1094,7 +1094,7 @@ static bool IsP4() word32 cpuid[4]; CpuId(0, cpuid); - mySTL::swap(cpuid[2], cpuid[3]); + STL::swap(cpuid[2], cpuid[3]); if (memcmp(cpuid+1, "GenuineIntel", 12) != 0) return false; @@ -2384,8 +2384,8 @@ void AsymmetricMultiply(word *R, word *T, const word *A, unsigned int NA, if (NA > NB) { - mySTL::swap(A, B); - mySTL::swap(NA, NB); + STL::swap(A, B); + STL::swap(NA, NB); } assert(NB % NA == 0); @@ -2521,8 +2521,8 @@ unsigned int AlmostInverse(word *R, word *T, const word *A, unsigned int NA, if (Compare(f, g, fgLen)==-1) { - mySTL::swap(f, g); - mySTL::swap(b, c); + STL::swap(f, g); + STL::swap(b, c); s++; } @@ -3162,7 +3162,7 @@ signed long Integer::ConvertToLong() const void Integer::Swap(Integer& a) { reg_.Swap(a.reg_); - mySTL::swap(sign_, a.sign_); + STL::swap(sign_, a.sign_); } diff --git a/extra/yassl/taocrypt/src/md4.cpp b/extra/yassl/taocrypt/src/md4.cpp index 6012330cba3..0dee8bf40cb 100644 --- a/extra/yassl/taocrypt/src/md4.cpp +++ b/extra/yassl/taocrypt/src/md4.cpp @@ -28,9 +28,11 @@ #include "runtime.hpp" #include "md4.hpp" -#include "algorithm.hpp" // mySTL::swap +#include STL_ALGORITHM_FILE +namespace STL = STL_NAMESPACE; + namespace TaoCrypt { @@ -69,9 +71,9 @@ MD4& MD4::operator= (const MD4& that) void MD4::Swap(MD4& other) { - mySTL::swap(loLen_, other.loLen_); - mySTL::swap(hiLen_, other.hiLen_); - mySTL::swap(buffLen_, other.buffLen_); + STL::swap(loLen_, other.loLen_); + STL::swap(hiLen_, other.hiLen_); + STL::swap(buffLen_, other.buffLen_); memcpy(digest_, other.digest_, DIGEST_SIZE); memcpy(buffer_, other.buffer_, BLOCK_SIZE); diff --git a/extra/yassl/taocrypt/src/md5.cpp b/extra/yassl/taocrypt/src/md5.cpp index f7b0b1ee2dc..2bddc7fe308 100644 --- a/extra/yassl/taocrypt/src/md5.cpp +++ b/extra/yassl/taocrypt/src/md5.cpp @@ -28,7 +28,10 @@ #include "runtime.hpp" #include "md5.hpp" -#include "algorithm.hpp" // mySTL::swap +#include STL_ALGORITHM_FILE + + +namespace STL = STL_NAMESPACE; #if defined(TAOCRYPT_X86ASM_AVAILABLE) && defined(TAO_ASM) @@ -72,9 +75,9 @@ MD5& MD5::operator= (const MD5& that) void MD5::Swap(MD5& other) { - mySTL::swap(loLen_, other.loLen_); - mySTL::swap(hiLen_, other.hiLen_); - mySTL::swap(buffLen_, other.buffLen_); + STL::swap(loLen_, other.loLen_); + STL::swap(hiLen_, other.hiLen_); + STL::swap(buffLen_, other.buffLen_); memcpy(digest_, other.digest_, DIGEST_SIZE); memcpy(buffer_, other.buffer_, BLOCK_SIZE); diff --git a/extra/yassl/taocrypt/src/misc.cpp b/extra/yassl/taocrypt/src/misc.cpp index a33ca4fa432..084a263a4ae 100644 --- a/extra/yassl/taocrypt/src/misc.cpp +++ b/extra/yassl/taocrypt/src/misc.cpp @@ -29,15 +29,6 @@ #include "runtime.hpp" #include "misc.hpp" -#if !defined(YASSL_MYSQL_COMPATIBLE) -extern "C" { - - // for libcurl configure test, these are the signatures they use - // locking handled internally by library - char CRYPTO_lock() { return 0;} - char CRYPTO_add_lock() { return 0;} -} // extern "C" -#endif #ifdef YASSL_PURE_C diff --git a/extra/yassl/taocrypt/src/random.cpp b/extra/yassl/taocrypt/src/random.cpp index 2ee1e57a663..c7bb6ae9549 100644 --- a/extra/yassl/taocrypt/src/random.cpp +++ b/extra/yassl/taocrypt/src/random.cpp @@ -31,7 +31,7 @@ #include "runtime.hpp" #include "random.hpp" #include <string.h> - +#include <time.h> #if defined(_WIN32) #define _WIN32_WINNT 0x0400 @@ -74,6 +74,8 @@ byte RandomNumberGenerator::GenerateByte() #if defined(_WIN32) +/* The OS_Seed implementation for windows */ + OS_Seed::OS_Seed() { if(!CryptAcquireContext(&handle_, 0, 0, PROV_RSA_FULL, @@ -95,8 +97,70 @@ void OS_Seed::GenerateSeed(byte* output, word32 sz) } -#else // _WIN32 +#elif defined(__NETWARE__) + +/* The OS_Seed implementation for Netware */ + +#include <nks/thread.h> +#include <nks/plat.h> + +// Loop on high resulution Read Time Stamp Counter +static void NetwareSeed(byte* output, word32 sz) +{ + word32 tscResult; + + for (word32 i = 0; i < sz; i += sizeof(tscResult)) { + #if defined(__GNUC__) + asm volatile("rdtsc" : "=A" (tscResult)); + #else + #ifdef __MWERKS__ + asm { + #else + __asm { + #endif + rdtsc + mov tscResult, eax + } + #endif + + memcpy(output, &tscResult, sizeof(tscResult)); + output += sizeof(tscResult); + + NXThreadYield(); // induce more variance + } +} + + +OS_Seed::OS_Seed() +{ +} + + +OS_Seed::~OS_Seed() +{ +} + + +void OS_Seed::GenerateSeed(byte* output, word32 sz) +{ + /* + Try to use NXSeedRandom as it will generate a strong + seed using the onboard 82802 chip + + As it's not always supported, fallback to default + implementation if an error is returned + */ + + if (NXSeedRandom(sz, output) != 0) + { + NetwareSeed(output, sz); + } +} + + +#else +/* The default OS_Seed implementation */ OS_Seed::OS_Seed() { diff --git a/extra/yassl/taocrypt/src/ripemd.cpp b/extra/yassl/taocrypt/src/ripemd.cpp index c791189544f..03c09edde84 100644 --- a/extra/yassl/taocrypt/src/ripemd.cpp +++ b/extra/yassl/taocrypt/src/ripemd.cpp @@ -28,9 +28,11 @@ #include "runtime.hpp" #include "ripemd.hpp" -#include "algorithm.hpp" // mySTL::swap +#include STL_ALGORITHM_FILE +namespace STL = STL_NAMESPACE; + #if defined(TAOCRYPT_X86ASM_AVAILABLE) && defined(TAO_ASM) #define DO_RIPEMD_ASM @@ -75,9 +77,9 @@ RIPEMD160& RIPEMD160::operator= (const RIPEMD160& that) void RIPEMD160::Swap(RIPEMD160& other) { - mySTL::swap(loLen_, other.loLen_); - mySTL::swap(hiLen_, other.hiLen_); - mySTL::swap(buffLen_, other.buffLen_); + STL::swap(loLen_, other.loLen_); + STL::swap(hiLen_, other.hiLen_); + STL::swap(buffLen_, other.buffLen_); memcpy(digest_, other.digest_, DIGEST_SIZE); memcpy(buffer_, other.buffer_, BLOCK_SIZE); diff --git a/extra/yassl/taocrypt/src/sha.cpp b/extra/yassl/taocrypt/src/sha.cpp index b877e2b7857..280d42fb3d4 100644 --- a/extra/yassl/taocrypt/src/sha.cpp +++ b/extra/yassl/taocrypt/src/sha.cpp @@ -27,8 +27,11 @@ #include "runtime.hpp" #include <string.h> -#include "algorithm.hpp" // mySTL::swap #include "sha.hpp" +#include STL_ALGORITHM_FILE + + +namespace STL = STL_NAMESPACE; #if defined(TAOCRYPT_X86ASM_AVAILABLE) && defined(TAO_ASM) @@ -96,9 +99,9 @@ SHA& SHA::operator= (const SHA& that) void SHA::Swap(SHA& other) { - mySTL::swap(loLen_, other.loLen_); - mySTL::swap(hiLen_, other.hiLen_); - mySTL::swap(buffLen_, other.buffLen_); + STL::swap(loLen_, other.loLen_); + STL::swap(hiLen_, other.hiLen_); + STL::swap(buffLen_, other.buffLen_); memcpy(digest_, other.digest_, DIGEST_SIZE); memcpy(buffer_, other.buffer_, BLOCK_SIZE); diff --git a/extra/yassl/taocrypt/src/template_instnt.cpp b/extra/yassl/taocrypt/src/template_instnt.cpp index 512c5cf9dce..db1ae645e09 100644 --- a/extra/yassl/taocrypt/src/template_instnt.cpp +++ b/extra/yassl/taocrypt/src/template_instnt.cpp @@ -77,6 +77,13 @@ template void destroy<vector<TaoCrypt::Integer>*>(vector<TaoCrypt::Integer>*, ve template TaoCrypt::Integer* uninit_copy<TaoCrypt::Integer*, TaoCrypt::Integer*>(TaoCrypt::Integer*, TaoCrypt::Integer*, TaoCrypt::Integer*); template TaoCrypt::Integer* uninit_fill_n<TaoCrypt::Integer*, size_t, TaoCrypt::Integer>(TaoCrypt::Integer*, size_t, TaoCrypt::Integer const&); template void destroy<TaoCrypt::Integer*>(TaoCrypt::Integer*, TaoCrypt::Integer*); +template TaoCrypt::byte* GetArrayMemory<TaoCrypt::byte>(size_t); +template void FreeArrayMemory<TaoCrypt::byte>(TaoCrypt::byte*); +template TaoCrypt::Integer* GetArrayMemory<TaoCrypt::Integer>(size_t); +template void FreeArrayMemory<TaoCrypt::Integer>(TaoCrypt::Integer*); +template vector<TaoCrypt::Integer>* GetArrayMemory<vector<TaoCrypt::Integer> >(size_t); +template void FreeArrayMemory<vector<TaoCrypt::Integer> >(vector<TaoCrypt::Integer>*); +template void FreeArrayMemory<void>(void*); } #endif diff --git a/extra/yassl/taocrypt/test/Makefile.am b/extra/yassl/taocrypt/test/Makefile.am index 0b238f1e057..988d00c7bef 100644 --- a/extra/yassl/taocrypt/test/Makefile.am +++ b/extra/yassl/taocrypt/test/Makefile.am @@ -1,8 +1,6 @@ -INCLUDES = -I../include -I../../mySTL +INCLUDES = -I../include -I../mySTL bin_PROGRAMS = test test_SOURCES = test.cpp -test_LDFLAGS = -L../src -test_LDADD = -ltaocrypt -test_DEPENDENCIES = ../src/libtaocrypt.la +test_LDADD = $(top_builddir)/extra/yassl/taocrypt/src/libtaocrypt.la test_CXXFLAGS = -DYASSL_PURE_C EXTRA_DIST = make.bat diff --git a/extra/yassl/testsuite/Makefile.am b/extra/yassl/testsuite/Makefile.am index 2ae46a1b409..e8abffd6bb0 100644 --- a/extra/yassl/testsuite/Makefile.am +++ b/extra/yassl/testsuite/Makefile.am @@ -1,11 +1,14 @@ -INCLUDES = -I../include -I../taocrypt/include -I../mySTL +INCLUDES = -I../include -I../taocrypt/include -I../taocrypt/mySTL bin_PROGRAMS = testsuite testsuite_SOURCES = testsuite.cpp ../taocrypt/test/test.cpp \ ../examples/client/client.cpp ../examples/server/server.cpp \ ../examples/echoclient/echoclient.cpp \ ../examples/echoserver/echoserver.cpp -testsuite_LDFLAGS = -L../src/ -L../taocrypt/src testsuite_CXXFLAGS = -DYASSL_PURE_C -DYASSL_PREFIX -DNO_MAIN_DRIVER -testsuite_LDADD = -lyassl -ltaocrypt -testsuite_DEPENDENCIES = ../src/libyassl.la ../taocrypt/src/libtaocrypt.la +testsuite_LDADD = $(top_builddir)/extra/yassl/src/libyassl.la \ + $(top_builddir)/extra/yassl/taocrypt/src/libtaocrypt.la EXTRA_DIST = testsuite.dsp test.hpp input quit make.bat + +# Don't update the files from bitkeeper +%::SCCS/s.% + diff --git a/extra/yassl/testsuite/test.hpp b/extra/yassl/testsuite/test.hpp index 482d384d415..0266c802657 100644 --- a/extra/yassl/testsuite/test.hpp +++ b/extra/yassl/testsuite/test.hpp @@ -27,24 +27,27 @@ #endif /* _WIN32 */ -#if !defined(_SOCKLEN_T) && defined(_WIN32) +#if !defined(_SOCKLEN_T) && (defined(_WIN32) || defined(__NETWARE__)) typedef int socklen_t; #endif +// Check type of third arg to accept +#if defined(__hpux) // HPUX doesn't use socklent_t for third parameter to accept -#if !defined(__hpux) - typedef socklen_t* ACCEPT_THIRD_T; -#else typedef int* ACCEPT_THIRD_T; +#else + typedef socklen_t* ACCEPT_THIRD_T; +#endif + +// Check if _POSIX_THREADS should be forced +#if !defined(_POSIX_THREADS) && (defined(__NETWARE__) || defined(__hpux)) // HPUX does not define _POSIX_THREADS as it's not _fully_ implemented -#ifndef _POSIX_THREADS +// Netware supports pthreads but does not announce it #define _POSIX_THREADS #endif -#endif - #ifndef _POSIX_THREADS typedef unsigned int THREAD_RETURN; @@ -148,6 +151,13 @@ inline void err_sys(const char* msg) } +static int PasswordCallBack(char* passwd, int sz, int rw, void* userdata) +{ + strncpy(passwd, "12345678", sz); + return 8; +} + + inline void store_ca(SSL_CTX* ctx) { // To allow testing from serveral dirs @@ -168,6 +178,7 @@ inline void store_ca(SSL_CTX* ctx) inline void set_certs(SSL_CTX* ctx) { store_ca(ctx); + SSL_CTX_set_default_passwd_cb(ctx, PasswordCallBack); // To allow testing from serveral dirs if (SSL_CTX_use_certificate_file(ctx, cert, SSL_FILETYPE_PEM) @@ -193,6 +204,7 @@ inline void set_certs(SSL_CTX* ctx) inline void set_serverCerts(SSL_CTX* ctx) { store_ca(ctx); + SSL_CTX_set_default_passwd_cb(ctx, PasswordCallBack); // To allow testing from serveral dirs if (SSL_CTX_use_certificate_file(ctx, svrCert, SSL_FILETYPE_PEM) @@ -258,13 +270,27 @@ inline void tcp_socket(SOCKET_T& sockfd, sockaddr_in& addr) } +inline void tcp_close(SOCKET_T& sockfd) +{ +#ifdef _WIN32 + closesocket(sockfd); +#else + close(sockfd); +#endif + sockfd = -1; +} + + inline void tcp_connect(SOCKET_T& sockfd) { sockaddr_in addr; tcp_socket(sockfd, addr); if (connect(sockfd, (const sockaddr*)&addr, sizeof(addr)) != 0) + { + tcp_close(sockfd); err_sys("tcp connect failed"); + } } @@ -274,13 +300,19 @@ inline void tcp_listen(SOCKET_T& sockfd) tcp_socket(sockfd, addr); if (bind(sockfd, (const sockaddr*)&addr, sizeof(addr)) != 0) + { + tcp_close(sockfd); err_sys("tcp bind failed"); + } if (listen(sockfd, 3) != 0) + { + tcp_close(sockfd); err_sys("tcp listen failed"); + } } -inline void tcp_accept(SOCKET_T& sockfd, int& clientfd, func_args& args) +inline void tcp_accept(SOCKET_T& sockfd, SOCKET_T& clientfd, func_args& args) { tcp_listen(sockfd); @@ -299,7 +331,10 @@ inline void tcp_accept(SOCKET_T& sockfd, int& clientfd, func_args& args) clientfd = accept(sockfd, (sockaddr*)&client, (ACCEPT_THIRD_T)&client_len); if (clientfd == -1) + { + tcp_close(sockfd); err_sys("tcp accept failed"); + } } diff --git a/include/m_ctype.h b/include/m_ctype.h index 54ae41bf2e0..0f5263e1c51 100644 --- a/include/m_ctype.h +++ b/include/m_ctype.h @@ -184,7 +184,7 @@ typedef struct my_charset_handler_st /* Charset dependant snprintf() */ int (*snprintf)(struct charset_info_st *, char *to, uint n, const char *fmt, - ...); + ...) ATTRIBUTE_FORMAT_FPTR(printf, 4, 5); int (*long10_to_str)(struct charset_info_st *, char *to, uint n, int radix, long int val); int (*longlong10_to_str)(struct charset_info_st *, char *to, uint n, @@ -205,6 +205,9 @@ typedef struct my_charset_handler_st int *err); longlong (*strtoll10)(struct charset_info_st *cs, const char *nptr, char **endptr, int *error); + ulonglong (*strntoull10rnd)(struct charset_info_st *cs, + const char *str, uint length, int unsigned_fl, + char **endptr, int *error); ulong (*scan)(struct charset_info_st *, const char *b, const char *e, int sq); } MY_CHARSET_HANDLER; @@ -319,7 +322,8 @@ int my_wc_mb_8bit(CHARSET_INFO *cs,my_wc_t wc, uchar *s, uchar *e); ulong my_scan_8bit(CHARSET_INFO *cs, const char *b, const char *e, int sq); int my_snprintf_8bit(struct charset_info_st *, char *to, uint n, - const char *fmt, ...); + const char *fmt, ...) + ATTRIBUTE_FORMAT(printf, 4, 5); long my_strntol_8bit(CHARSET_INFO *, const char *s, uint l, int base, char **e, int *err); @@ -341,6 +345,13 @@ longlong my_strtoll10_8bit(CHARSET_INFO *cs, longlong my_strtoll10_ucs2(CHARSET_INFO *cs, const char *nptr, char **endptr, int *error); +ulonglong my_strntoull10rnd_8bit(CHARSET_INFO *cs, + const char *str, uint length, int unsigned_fl, + char **endptr, int *error); +ulonglong my_strntoull10rnd_ucs2(CHARSET_INFO *cs, + const char *str, uint length, int unsigned_fl, + char **endptr, int *error); + void my_fill_8bit(CHARSET_INFO *cs, char* to, uint l, int fill); my_bool my_like_range_simple(CHARSET_INFO *cs, diff --git a/include/m_string.h b/include/m_string.h index c02ce92cd88..8a526d70d1d 100644 --- a/include/m_string.h +++ b/include/m_string.h @@ -254,7 +254,8 @@ extern ulonglong strtoull(const char *str, char **ptr, int base); extern int my_vsnprintf( char *str, size_t n, const char *format, va_list ap ); -extern int my_snprintf(char* to, size_t n, const char* fmt, ...); +extern int my_snprintf(char *to, size_t n, const char *fmt, ...) + ATTRIBUTE_FORMAT(printf, 3, 4); #if defined(__cplusplus) && !defined(OS2) } diff --git a/include/my_global.h b/include/my_global.h index 4a9e1673de4..f94cedbc91a 100644 --- a/include/my_global.h +++ b/include/my_global.h @@ -454,12 +454,50 @@ typedef unsigned short ushort; #define function_volatile volatile #define my_reinterpret_cast(A) reinterpret_cast<A> #define my_const_cast(A) const_cast<A> +# ifndef GCC_VERSION +# define GCC_VERSION (__GNUC__ * 1000 + __GNUC_MINOR__) +# endif #elif !defined(my_reinterpret_cast) #define my_reinterpret_cast(A) (A) #define my_const_cast(A) (A) #endif -#if !defined(__attribute__) && (defined(__cplusplus) || !defined(__GNUC__) || __GNUC__ == 2 && __GNUC_MINOR__ < 8) -#define __attribute__(A) + +/* + Disable __attribute__() on gcc < 2.7, g++ < 3.4, and non-gcc compilers. + Some forms of __attribute__ are actually supported in earlier versions of + g++, but we just disable them all because we only use them to generate + compilation warnings. +*/ +#ifndef __attribute__ +# if !defined(__GNUC__) +# define __attribute__(A) +# elif GCC_VERSION < 2008 +# define __attribute__(A) +# elif defined(__cplusplus) && GCC_VERSION < 3004 +# define __attribute__(A) +# endif +#endif + +/* + __attribute__((format(...))) is only supported in gcc >= 2.8 and g++ >= 3.4 + But that's already covered by the __attribute__ tests above, so this is + just a convenience macro. +*/ +#ifndef ATTRIBUTE_FORMAT +# define ATTRIBUTE_FORMAT(style, m, n) __attribute__((format(style, m, n))) +#endif + +/* + + __attribute__((format(...))) on a function pointer is not supported + until gcc 3.1 +*/ +#ifndef ATTRIBUTE_FORMAT_FPTR +# if (GCC_VERSION >= 3001) +# define ATTRIBUTE_FORMAT_FPTR(style, m, n) ATTRIBUTE_FORMAT(style, m, n) +# else +# define ATTRIBUTE_FORMAT_FPTR(style, m, n) +# endif /* GNUC >= 3.1 */ #endif /* diff --git a/include/my_sys.h b/include/my_sys.h index 9b283ace029..2c0ef955477 100644 --- a/include/my_sys.h +++ b/include/my_sys.h @@ -632,8 +632,8 @@ extern int my_chsize(File fd,my_off_t newlength, int filler, myf MyFlags); extern int my_sync(File fd, myf my_flags); extern int my_error _VARARGS((int nr,myf MyFlags, ...)); extern int my_printf_error _VARARGS((uint my_err, const char *format, - myf MyFlags, ...) - __attribute__ ((format (printf, 2, 4)))); + myf MyFlags, ...)) + ATTRIBUTE_FORMAT(printf, 2, 4); extern int my_error_register(const char **errmsgs, int first, int last); extern const char **my_error_unregister(int first, int last); extern int my_message(uint my_err, const char *str,myf MyFlags); diff --git a/include/mysql_com.h b/include/mysql_com.h index 4c7640376a6..1bbb3cf1737 100644 --- a/include/mysql_com.h +++ b/include/mysql_com.h @@ -134,11 +134,11 @@ enum enum_server_command #define CLIENT_TRANSACTIONS 8192 /* Client knows about transactions */ #define CLIENT_RESERVED 16384 /* Old flag for 4.1 protocol */ #define CLIENT_SECURE_CONNECTION 32768 /* New 4.1 authentication */ -#define CLIENT_MULTI_STATEMENTS (((ulong) 1) << 16) /* Enable/disable multi-stmt support */ -#define CLIENT_MULTI_RESULTS (((ulong) 1) << 17) /* Enable/disable multi-results */ +#define CLIENT_MULTI_STATEMENTS (1UL << 16) /* Enable/disable multi-stmt support */ +#define CLIENT_MULTI_RESULTS (1UL << 17) /* Enable/disable multi-results */ -#define CLIENT_SSL_VERIFY_SERVER_CERT (((ulong) 1) << 30) -#define CLIENT_REMEMBER_OPTIONS (((ulong) 1) << 31) +#define CLIENT_SSL_VERIFY_SERVER_CERT (1UL << 30) +#define CLIENT_REMEMBER_OPTIONS (1UL << 31) #define SERVER_STATUS_IN_TRANS 1 /* Transaction has started */ #define SERVER_STATUS_AUTOCOMMIT 2 /* Server in auto_commit mode */ diff --git a/innobase/ibuf/ibuf0ibuf.c b/innobase/ibuf/ibuf0ibuf.c index 9c7d9c5c3da..eb10a88d1d1 100644 --- a/innobase/ibuf/ibuf0ibuf.c +++ b/innobase/ibuf/ibuf0ibuf.c @@ -1361,8 +1361,8 @@ ibuf_entry_build( index tree; NOTE that the original entry must be kept because we copy pointers to its fields */ + dict_index_t* index, /* in: non-clustered index */ dtuple_t* entry, /* in: entry for a non-clustered index */ - ibool comp, /* in: flag: TRUE=compact record format */ ulint space, /* in: space id */ ulint page_no,/* in: index page number where entry should be inserted */ @@ -1426,13 +1426,13 @@ ibuf_entry_build( dfield_set_data(field, buf, 4); - ut_ad(comp == 0 || comp == 1); + ut_ad(index->table->comp <= 1); /* Store the type info in buf2, and add the fields from entry to tuple */ buf2 = mem_heap_alloc(heap, n_fields * DATA_NEW_ORDER_NULL_TYPE_BUF_SIZE - + comp); - if (comp) { + + index->table->comp); + if (index->table->comp) { *buf2++ = 0; /* write the compact format indicator */ } for (i = 0; i < n_fields; i++) { @@ -1445,20 +1445,22 @@ ibuf_entry_build( dtype_new_store_for_order_and_null_size( buf2 + i * DATA_NEW_ORDER_NULL_TYPE_BUF_SIZE, - dfield_get_type(entry_field)); + dfield_get_type(entry_field), + dict_index_get_nth_field(index, i) + ->prefix_len); } /* Store the type info in buf2 to field 3 of tuple */ field = dtuple_get_nth_field(tuple, 3); - if (comp) { + if (index->table->comp) { buf2--; } dfield_set_data(field, buf2, n_fields * DATA_NEW_ORDER_NULL_TYPE_BUF_SIZE - + comp); + + index->table->comp); /* Set all the types in the new tuple binary */ dtuple_set_types_binary(tuple, n_fields + 4); @@ -2589,8 +2591,7 @@ ibuf_insert_low( the first fields and the type information for other fields, and which will be inserted to the insert buffer. */ - ibuf_entry = ibuf_entry_build(entry, index->table->comp, - space, page_no, heap); + ibuf_entry = ibuf_entry_build(index, entry, space, page_no, heap); /* Open a cursor to the insert buffer tree to calculate if we can add the new entry to it without exceeding the free space limit for the diff --git a/innobase/include/data0type.h b/innobase/include/data0type.h index 30c0f732c34..abfbc24e336 100644 --- a/innobase/include/data0type.h +++ b/innobase/include/data0type.h @@ -366,7 +366,9 @@ dtype_new_store_for_order_and_null_size( byte* buf, /* in: buffer for DATA_NEW_ORDER_NULL_TYPE_BUF_SIZE bytes where we store the info */ - dtype_t* type); /* in: type struct */ + dtype_t* type, /* in: type struct */ + ulint prefix_len);/* in: prefix length to + replace type->len, or 0 */ /************************************************************************** Reads to a type the stored information which determines its alphabetical ordering and the storage size of an SQL NULL value. This is the 4.1.x storage diff --git a/innobase/include/data0type.ic b/innobase/include/data0type.ic index ad0f02fa63d..032c1d7efd7 100644 --- a/innobase/include/data0type.ic +++ b/innobase/include/data0type.ic @@ -230,11 +230,14 @@ dtype_new_store_for_order_and_null_size( byte* buf, /* in: buffer for DATA_NEW_ORDER_NULL_TYPE_BUF_SIZE bytes where we store the info */ - dtype_t* type) /* in: type struct */ + dtype_t* type, /* in: type struct */ + ulint prefix_len)/* in: prefix length to + replace type->len, or 0 */ { #if 6 != DATA_NEW_ORDER_NULL_TYPE_BUF_SIZE #error "6 != DATA_NEW_ORDER_NULL_TYPE_BUF_SIZE" #endif + ulint len; buf[0] = (byte)(type->mtype & 0xFFUL); @@ -249,7 +252,9 @@ dtype_new_store_for_order_and_null_size( buf[1] = (byte)(type->prtype & 0xFFUL); - mach_write_to_2(buf + 2, type->len & 0xFFFFUL); + len = prefix_len ? prefix_len : type->len; + + mach_write_to_2(buf + 2, len & 0xFFFFUL); ut_ad(dtype_get_charset_coll(type->prtype) < 256); mach_write_to_2(buf + 4, dtype_get_charset_coll(type->prtype)); diff --git a/innobase/include/univ.i b/innobase/include/univ.i index bc3bd031f0c..64a240ae8a7 100644 --- a/innobase/include/univ.i +++ b/innobase/include/univ.i @@ -39,8 +39,10 @@ if we are compiling on Windows. */ #undef PACKAGE #undef VERSION +#if !defined(__WIN__) && !defined(WIN64) && !defined(_WIN64) /* Include the header file generated by GNU autoconf */ #include "../ib_config.h" +#endif #ifdef HAVE_SCHED_H #include <sched.h> diff --git a/innobase/srv/srv0start.c b/innobase/srv/srv0start.c index 6e0dc720bf8..8530f117c9d 100644 --- a/innobase/srv/srv0start.c +++ b/innobase/srv/srv0start.c @@ -1140,7 +1140,7 @@ innobase_start_or_create_for_mysql(void) maximum number of threads that can wait in the 'srv_conc array' for their time to enter InnoDB. */ -#if defined(__WIN__) || defined(__NETWARE__) +#if defined(__NETWARE__) /* Create less event semaphores because Win 98/ME had difficulty creating 40000 event semaphores. diff --git a/myisam/mi_locking.c b/myisam/mi_locking.c index 8d48c5242e5..36b793363c5 100644 --- a/myisam/mi_locking.c +++ b/myisam/mi_locking.c @@ -224,6 +224,21 @@ int mi_lock_database(MI_INFO *info, int lock_type) break; /* Impossible */ } } +#ifdef __WIN__ + else + { + /* + Check for bad file descriptors if this table is part + of a merge union. Failing to capture this may cause + a crash on windows if the table is renamed and + later on referenced by the merge table. + */ + if( info->owned_by_merge && (info->s)->kfile < 0 ) + { + error = HA_ERR_NO_SUCH_TABLE; + } + } +#endif pthread_mutex_unlock(&share->intern_lock); #if defined(FULL_LOG) || defined(_lint) lock_type|=(int) (flag << 8); /* Set bit to set if real lock */ diff --git a/myisam/myisamdef.h b/myisam/myisamdef.h index d589173f0e7..ea45915a088 100644 --- a/myisam/myisamdef.h +++ b/myisam/myisamdef.h @@ -278,6 +278,9 @@ struct st_myisam_info { my_bool page_changed; /* If info->buff can't be used for rnext */ my_bool buff_used; /* If info->buff has to be reread for rnext */ my_bool once_flags; /* For MYISAMMRG */ +#ifdef __WIN__ + my_bool owned_by_merge; /* This MyISAM table is part of a merge union */ +#endif #ifdef THREAD THR_LOCK_DATA lock; #endif diff --git a/myisammrg/myrg_locking.c b/myisammrg/myrg_locking.c index e5a8d3f3d9d..98e8305b9ce 100644 --- a/myisammrg/myrg_locking.c +++ b/myisammrg/myrg_locking.c @@ -26,8 +26,19 @@ int myrg_lock_database(MYRG_INFO *info, int lock_type) MYRG_TABLE *file; error=0; - for (file=info->open_tables ; file != info->end_table ; file++) + for (file=info->open_tables ; file != info->end_table ; file++) + { +#ifdef __WIN__ + /* + Make sure this table is marked as owned by a merge table. + The semaphore is never released as long as table remains + in memory. This should be refactored into a more generic + approach (observer pattern) + */ + (file->table)->owned_by_merge = TRUE; +#endif if ((new_error=mi_lock_database(file->table,lock_type))) error=new_error; + } return(error); } diff --git a/mysql-test/lib/mtr_process.pl b/mysql-test/lib/mtr_process.pl index a11747d5a42..00b12ba5fb5 100644 --- a/mysql-test/lib/mtr_process.pl +++ b/mysql-test/lib/mtr_process.pl @@ -455,14 +455,6 @@ sub mtr_kill_leftovers () { mtr_debug("Got pid: $pid from file '$pidfile'"); - # Race, could have been removed between I tested with -f - # and the unlink() below, so I better check again with -f - - if ( ! unlink($pidfile) and -f $pidfile ) - { - mtr_error("can't remove $pidfile"); - } - if ( $::glob_cygwin_perl or kill(0, $pid) ) { mtr_debug("There is process with pid $pid -- scheduling for kill."); diff --git a/mysql-test/lib/mtr_stress.pl b/mysql-test/lib/mtr_stress.pl index 77c3d8bb030..92bb220461b 100644 --- a/mysql-test/lib/mtr_stress.pl +++ b/mysql-test/lib/mtr_stress.pl @@ -21,7 +21,6 @@ sub run_stress_test () { my $args; - my $stress_basedir; my $stress_suitedir; mtr_report("Starting stress testing\n"); diff --git a/mysql-test/mysql-test-run.pl b/mysql-test/mysql-test-run.pl index 06dd3864212..13ce7ccc66e 100755 --- a/mysql-test/mysql-test-run.pl +++ b/mysql-test/mysql-test-run.pl @@ -256,7 +256,7 @@ our $opt_result_ext; our $opt_skip; our $opt_skip_rpl; -our $use_slaves; +our $max_slave_num= 0; our $opt_skip_test; our $opt_skip_im; @@ -267,7 +267,7 @@ our $opt_sleep_time_for_delete= 10; our $opt_testcase_timeout; our $opt_suite_timeout; my $default_testcase_timeout= 15; # 15 min max -my $default_suite_timeout= 120; # 2 hours max +my $default_suite_timeout= 180; # 3 hours max our $opt_socket; @@ -410,7 +410,13 @@ sub main () { { $need_ndbcluster||= $test->{ndb_test}; $need_im||= $test->{component_id} eq 'im'; - $use_slaves||= $test->{slave_num}; + + # Count max number of slaves used by a test case + if ( $test->{slave_num} > $max_slave_num) + { + $max_slave_num= $test->{slave_num}; + mtr_error("Too many slaves") if $max_slave_num > 3; + } } $opt_with_ndbcluster= 0 unless $need_ndbcluster; $opt_skip_im= 1 unless $need_im; @@ -845,13 +851,13 @@ sub command_line_setup () { if ( ! $opt_testcase_timeout ) { $opt_testcase_timeout= $default_testcase_timeout; - $opt_testcase_timeout*= 10 if defined $opt_valgrind; + $opt_testcase_timeout*= 10 if $opt_valgrind; } if ( ! $opt_suite_timeout ) { $opt_suite_timeout= $default_suite_timeout; - $opt_suite_timeout*= 4 if defined $opt_valgrind; + $opt_suite_timeout*= 6 if $opt_valgrind; } # Increase times to wait for executables to start if using valgrind @@ -996,11 +1002,9 @@ sub snapshot_setup () { $master->[0]->{'path_myddir'}, $master->[1]->{'path_myddir'}); - if ($use_slaves) + for (my $idx= 0; $idx < $max_slave_num; $idx++) { - push @data_dir_lst, ($slave->[0]->{'path_myddir'}, - $slave->[1]->{'path_myddir'}, - $slave->[2]->{'path_myddir'}); + push(@data_dir_lst, $slave->[$idx]->{'path_myddir'}); } unless ($opt_skip_im) @@ -1194,7 +1198,7 @@ sub executable_setup () { sub environment_setup () { - my $extra_ld_library_paths; + my @ld_library_paths; # -------------------------------------------------------------------------- # Setup LD_LIBRARY_PATH so the libraries from this distro/clone @@ -1202,25 +1206,40 @@ sub environment_setup () { # -------------------------------------------------------------------------- if ( $opt_source_dist ) { - $extra_ld_library_paths= "$glob_basedir/libmysql/.libs/"; + push(@ld_library_paths, "$glob_basedir/libmysql/.libs/") } else { - $extra_ld_library_paths= "$glob_basedir/lib"; + push(@ld_library_paths, "$glob_basedir/lib") } # -------------------------------------------------------------------------- # Add the path where mysqld will find udf_example.so # -------------------------------------------------------------------------- - $extra_ld_library_paths .= ":" . - ($lib_udf_example ? dirname($lib_udf_example) : ""); + if ( $lib_udf_example ) + { + push(@ld_library_paths, dirname($lib_udf_example)); + } + + # -------------------------------------------------------------------------- + #Valgrind need to be run with debug libraries otherwise it's almost + # impossible to add correct supressions, that means if "/usr/lib/debug" + # is available, it should be added to + # LD_LIBRARY_PATH + # -------------------------------------------------------------------------- + my $debug_libraries_path= "/usr/lib/debug"; + if ( $opt_valgrind and -d $debug_libraries_path ) + { + push(@ld_library_paths, $debug_libraries_path); + } - $ENV{'LD_LIBRARY_PATH'}= - "$extra_ld_library_paths" . - ($ENV{'LD_LIBRARY_PATH'} ? ":$ENV{'LD_LIBRARY_PATH'}" : ""); - $ENV{'DYLD_LIBRARY_PATH'}= - "$extra_ld_library_paths" . - ($ENV{'DYLD_LIBRARY_PATH'} ? ":$ENV{'DYLD_LIBRARY_PATH'}" : ""); + $ENV{'LD_LIBRARY_PATH'}= join(":", @ld_library_paths, + split(':', $ENV{'LD_LIBRARY_PATH'})); + mtr_debug("LD_LIBRARY_PATH: $ENV{'LD_LIBRARY_PATH'}"); + + $ENV{'DYLD_LIBRARY_PATH'}= join(":", @ld_library_paths, + split(':', $ENV{'DYLD_LIBRARY_PATH'})); + mtr_debug("DYLD_LIBRARY_PATH: $ENV{'DYLD_LIBRARY_PATH'}"); # -------------------------------------------------------------------------- # Also command lines in .opt files may contain env vars @@ -1314,7 +1333,7 @@ sub kill_running_server () { { # Ensure that no old mysqld test servers are running # This is different from terminating processes we have - # started from ths run of the script, this is terminating + # started from this run of the script, this is terminating # leftovers from previous runs. mtr_kill_leftovers(); @@ -1721,15 +1740,13 @@ sub initialize_servers () { sub mysql_install_db () { - # FIXME not exactly true I think, needs improvements - install_db('master', $master->[0]->{'path_myddir'}); - install_db('master', $master->[1]->{'path_myddir'}); + install_db('master1', $master->[0]->{'path_myddir'}); + copy_install_db('master2', $master->[1]->{'path_myddir'}); - if ( $use_slaves ) + # Install the number of slave databses needed + for (my $idx= 0; $idx < $max_slave_num; $idx++) { - install_db('slave', $slave->[0]->{'path_myddir'}); - install_db('slave', $slave->[1]->{'path_myddir'}); - install_db('slave', $slave->[2]->{'path_myddir'}); + copy_install_db("slave".($idx+1), $slave->[$idx]->{'path_myddir'}); } if ( ! $opt_skip_im ) @@ -1759,6 +1776,17 @@ sub mysql_install_db () { } +sub copy_install_db ($$) { + my $type= shift; + my $data_dir= shift; + + mtr_report("Installing \u$type Database"); + + # Just copy the installed db from first master + mtr_copy_dir($master->[0]->{'path_myddir'}, $data_dir); + +} + sub install_db ($$) { my $type= shift; my $data_dir= shift; @@ -1805,6 +1833,12 @@ sub install_db ($$) { mtr_add_arg($args, "--skip-ndbcluster"); mtr_add_arg($args, "--skip-bdb"); + if ( $opt_debug ) + { + mtr_add_arg($args, "--debug=d:t:i:A,%s/log/bootstrap_%s.trace", + $opt_vardir_trace, $type); + } + if ( ! $opt_netware ) { mtr_add_arg($args, "--language=%s", $path_language); @@ -1913,13 +1947,33 @@ sub im_prepare_data_dir($) { foreach my $instance (@{$instance_manager->{'instances'}}) { - install_db( + copy_install_db( 'im_mysqld_' . $instance->{'server_id'}, $instance->{'path_datadir'}); } } +# +# Restore snapshot of the installed slave databases +# if the snapshot exists +# +sub restore_slave_databases () { + + if ( -d $path_snapshot) + { + # Restore the number of slave databases being used + for (my $idx= 0; $idx < $max_slave_num; $idx++) + { + my $data_dir= $slave->[$idx]->{'path_myddir'}; + my $name= basename($data_dir); + rmtree($data_dir); + mtr_copy_dir("$path_snapshot/$name", $data_dir); + } + } +} + + ############################################################################## # # Run a single test case @@ -2020,6 +2074,7 @@ sub run_testcase ($) { # ---------------------------------------------------------------------- stop_slaves(); + restore_slave_databases(); } # ---------------------------------------------------------------------- @@ -2410,7 +2465,7 @@ sub do_before_start_slave ($$) { sub mysqld_arguments ($$$$$$) { my $args= shift; - my $type= shift; # master/slave/bootstrap + my $type= shift; # master/slave my $idx= shift; my $extra_opt= shift; my $slave_master_info= shift; @@ -2639,7 +2694,7 @@ sub mysqld_arguments ($$$$$$) { ############################################################################## sub mysqld_start ($$$$$) { - my $type= shift; # master/slave/bootstrap + my $type= shift; # master/slave my $idx= shift; my $extra_opt= shift; my $slave_master_info= shift; @@ -2660,7 +2715,7 @@ sub mysqld_start ($$$$$) { } else { - $exe= $exe_mysqld; + mtr_error("Unknown 'type' passed to mysqld_start"); } mtr_init_args(\$args); @@ -2762,7 +2817,7 @@ sub stop_masters () { my @args; - for ( my $idx; $idx < 2; $idx++ ) + for ( my $idx= 0; $idx < 2; $idx++ ) { # FIXME if we hit ^C before fully started, this test will prevent # the mysqld process from being killed @@ -2793,7 +2848,7 @@ sub stop_slaves () { my @args; - for ( my $idx; $idx < 3; $idx++ ) + for ( my $idx= 0; $idx < $max_slave_num; $idx++ ) { if ( $slave->[$idx]->{'pid'} ) { @@ -2911,7 +2966,8 @@ sub run_mysqltest ($) { my $cmdline_mysql= "$exe_mysql --host=localhost --user=root --password= " . "--port=$master->[0]->{'path_myport'} " . - "--socket=$master->[0]->{'path_mysock'}"; + "--socket=$master->[0]->{'path_mysock'} ". + "--character-sets-dir=$path_charsetsdir"; my $cmdline_mysql_client_test= "$exe_mysql_client_test --no-defaults --testcase --user=root --silent " . diff --git a/mysql-test/r/analyse.result b/mysql-test/r/analyse.result index 56f67cce4d6..0ecc462fb70 100644 --- a/mysql-test/r/analyse.result +++ b/mysql-test/r/analyse.result @@ -141,3 +141,16 @@ test.t1.product Computer TV 2 8 0 0 4.2500 NULL ENUM('Computer','Phone','TV') NO sum(profit) 10 6900 11 11 0 0 1946.2500 2867.6719 ENUM('10','275','600','6900') NOT NULL avg(profit) 10.0000 1380.0000 16 16 0 0 394.68750000 570.20033144 ENUM('10.0000','68.7500','120.0000','1380.0000') NOT NULL drop table t1,t2; +create table t1 (f1 double(10,5), f2 char(10), f3 double(10,5)); +insert into t1 values (5.999, "5.9999", 5.99999), (9.555, "9.5555", 9.55555); +select f1 from t1 procedure analyse(1, 1); +Field_name Min_value Max_value Min_length Max_length Empties_or_zeros Nulls Avg_value_or_avg_length Std Optimal_fieldtype +test.t1.f1 5.99900 9.55500 7 7 0 0 7.77700 1.77800 FLOAT(4,3) NOT NULL +select f2 from t1 procedure analyse(1, 1); +Field_name Min_value Max_value Min_length Max_length Empties_or_zeros Nulls Avg_value_or_avg_length Std Optimal_fieldtype +test.t1.f2 5.9999 9.5555 6 6 0 0 6.0000 NULL FLOAT(5,4) UNSIGNED NOT NULL +select f3 from t1 procedure analyse(1, 1); +Field_name Min_value Max_value Min_length Max_length Empties_or_zeros Nulls Avg_value_or_avg_length Std Optimal_fieldtype +test.t1.f3 5.99999 9.55555 7 7 0 0 7.77777 1.77778 FLOAT(6,5) NOT NULL +drop table t1; +End of 4.1 tests diff --git a/mysql-test/r/client_xml.result b/mysql-test/r/client_xml.result index 24c05c7f9d6..7395b2433e8 100644 --- a/mysql-test/r/client_xml.result +++ b/mysql-test/r/client_xml.result @@ -68,7 +68,7 @@ insert into t1 values (1, 2, 'a&b a<b a>b'); <resultset statement="select null from dual "> <row> - <field name="NULL">NULL</field> + <field name="NULL" xsi:nil="true" /> </row> </resultset> drop table t1; diff --git a/mysql-test/r/ctype_gbk.result b/mysql-test/r/ctype_gbk.result index 241539ecf42..3f5d8b0d8c6 100644 --- a/mysql-test/r/ctype_gbk.result +++ b/mysql-test/r/ctype_gbk.result @@ -168,3 +168,13 @@ DROP TABLE t1; select hex(convert(_gbk 0xA14041 using ucs2)); hex(convert(_gbk 0xA14041 using ucs2)) 003F0041 +create table t1 (c1 text not null, c2 text not null) character set gbk; +alter table t1 change c1 c1 mediumtext character set gbk not null; +show create table t1; +Table Create Table +t1 CREATE TABLE `t1` ( + `c1` mediumtext NOT NULL, + `c2` text NOT NULL +) ENGINE=MyISAM DEFAULT CHARSET=gbk +drop table t1; +End of 5.0 tests diff --git a/mysql-test/r/ctype_utf8.result b/mysql-test/r/ctype_utf8.result index bf271437fac..fd46f36227b 100644 --- a/mysql-test/r/ctype_utf8.result +++ b/mysql-test/r/ctype_utf8.result @@ -1340,6 +1340,18 @@ select a from t1 group by a; a e drop table t1; +create table t1(a char(10)) default charset utf8; +insert into t1 values ('123'), ('456'); +explain +select substr(Z.a,-1), Z.a from t1 as Y join t1 as Z on Y.a=Z.a order by 1; +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE Y ALL NULL NULL NULL NULL 2 Using temporary; Using filesort +1 SIMPLE Z ALL NULL NULL NULL NULL 2 Using where +select substr(Z.a,-1), Z.a from t1 as Y join t1 as Z on Y.a=Z.a order by 1; +substr(Z.a,-1) a +3 123 +6 456 +drop table t1; CREATE TABLE t1(id varchar(20) NOT NULL) DEFAULT CHARSET=utf8; INSERT INTO t1 VALUES ('xxx'), ('aa'), ('yyy'), ('aa'); SELECT id FROM t1; @@ -1449,3 +1461,21 @@ set @a:=null; execute my_stmt using @a; a b drop table if exists t1; +CREATE TABLE t1 ( +colA int(11) NOT NULL, +colB varchar(255) character set utf8 NOT NULL, +PRIMARY KEY (colA) +) ENGINE=InnoDB DEFAULT CHARSET=latin1; +INSERT INTO t1 (colA, colB) VALUES (1, 'foo'), (2, 'foo bar'); +CREATE TABLE t2 ( +colA int(11) NOT NULL, +colB varchar(255) character set utf8 NOT NULL, +KEY bad (colA,colB(3)) +) ENGINE=InnoDB DEFAULT CHARSET=latin1; +INSERT INTO t2 (colA, colB) VALUES (1, 'foo'),(2, 'foo bar'); +SELECT * FROM t1 JOIN t2 ON t1.colA=t2.colA AND t1.colB=t2.colB +WHERE t1.colA < 3; +colA colB colA colB +1 foo 1 foo +2 foo bar 2 foo bar +DROP TABLE t1, t2; diff --git a/mysql-test/r/execution_constants.result b/mysql-test/r/execution_constants.result new file mode 100644 index 00000000000..293c88dc506 --- /dev/null +++ b/mysql-test/r/execution_constants.result @@ -0,0 +1,12 @@ +CREATE TABLE `t_bug21476` ( +`ID_BOARD` smallint(5) unsigned NOT NULL default '0', +`ID_MEMBER` mediumint(8) unsigned NOT NULL default '0', +`logTime` int(10) unsigned NOT NULL default '0', +`ID_MSG` mediumint(8) unsigned NOT NULL default '0', +PRIMARY KEY (`ID_MEMBER`,`ID_BOARD`), +KEY `logTime` (`logTime`) +) ENGINE=MyISAM DEFAULT CHARSET=cp1251 COLLATE=cp1251_bulgarian_ci; +INSERT INTO `t_bug21476` VALUES (2,2,1154870939,0),(1,2,1154870957,0),(2,183,1154941362,0),(2,84,1154904301,0),(1,84,1154905867,0),(2,13,1154947484,10271),(3,84,1154880549,0),(1,6,1154892183,0),(2,25,1154947581,10271),(3,25,1154904760,0),(1,25,1154947373,10271),(1,179,1154899992,0),(2,179,1154899410,0),(5,25,1154901666,0),(2,329,1154902026,0),(3,329,1154902040,0),(1,329,1154902058,0),(1,13,1154930841,0),(3,85,1154904987,0),(1,183,1154929665,0),(3,13,1154931268,0),(1,85,1154936888,0),(1,169,1154937959,0),(2,169,1154941717,0),(3,183,1154939810,0),(3,169,1154941734,0); +Assertion: mysql_errno 1436 == 1436 +DROP TABLE `t_bug21476`; +End of 5.0 tests. diff --git a/mysql-test/r/func_time.result b/mysql-test/r/func_time.result index 9fea857e4e5..25c910a711a 100644 --- a/mysql-test/r/func_time.result +++ b/mysql-test/r/func_time.result @@ -890,6 +890,18 @@ t1 CREATE TABLE `t1` ( `from_unixtime(1) + 0` double(23,6) default NULL ) ENGINE=MyISAM DEFAULT CHARSET=latin1 drop table t1; +SET NAMES latin1; +SET character_set_results = NULL; +SHOW VARIABLES LIKE 'character_set_results'; +Variable_name Value +character_set_results +CREATE TABLE testBug8868 (field1 DATE, field2 VARCHAR(32) CHARACTER SET BINARY); +INSERT INTO testBug8868 VALUES ('2006-09-04', 'abcd'); +SELECT DATE_FORMAT(field1,'%b-%e %l:%i%p') as fmtddate, field2 FROM testBug8868; +fmtddate field2 +Sep-4 12:00AM abcd +DROP TABLE testBug8868; +SET NAMES DEFAULT; (select time_format(timediff(now(), DATE_SUB(now(),INTERVAL 5 DAY)),'%H') As H) union (select time_format(timediff(now(), DATE_SUB(now(),INTERVAL 5 DAY)),'%H') As H); diff --git a/mysql-test/r/loaddata.result b/mysql-test/r/loaddata.result index 17e1966dbc9..d415bd468e0 100644 --- a/mysql-test/r/loaddata.result +++ b/mysql-test/r/loaddata.result @@ -43,9 +43,9 @@ drop table t1; create table t1 (a int, b char(10)); load data infile '../std_data_ln/loaddata3.dat' into table t1 fields terminated by '' enclosed by '' ignore 1 lines; Warnings: -Warning 1264 Out of range value adjusted for column 'a' at row 3 +Warning 1366 Incorrect integer value: 'error ' for column 'a' at row 3 Warning 1262 Row 3 was truncated; it contained more data than there were input columns -Warning 1264 Out of range value adjusted for column 'a' at row 5 +Warning 1366 Incorrect integer value: 'wrong end ' for column 'a' at row 5 Warning 1262 Row 5 was truncated; it contained more data than there were input columns select * from t1; a b @@ -57,7 +57,8 @@ a b truncate table t1; load data infile '../std_data_ln/loaddata4.dat' into table t1 fields terminated by '' enclosed by '' lines terminated by '' ignore 1 lines; Warnings: -Warning 1264 Out of range value adjusted for column 'a' at row 4 +Warning 1366 Incorrect integer value: ' +' for column 'a' at row 4 Warning 1261 Row 4 doesn't contain data for all columns select * from t1; a b diff --git a/mysql-test/r/mysqltest.result b/mysql-test/r/mysqltest.result index d9ca863b6bc..123091841df 100644 --- a/mysql-test/r/mysqltest.result +++ b/mysql-test/r/mysqltest.result @@ -217,8 +217,11 @@ hej a long variable content a long variable content -a long $where variable content +a long a long variable content variable content +a long \$where variable content +banana = banana +Not a banana: ba\$cat\$cat mysqltest: At line 1: Missing arguments to let mysqltest: At line 1: Missing variable name in let mysqltest: At line 1: Variable name in hi=hi does not start with '$' diff --git a/mysql-test/r/ps_2myisam.result b/mysql-test/r/ps_2myisam.result index 205c084b71f..2a7b0e959af 100644 --- a/mysql-test/r/ps_2myisam.result +++ b/mysql-test/r/ps_2myisam.result @@ -2689,21 +2689,21 @@ set @arg00= '1.11111111111111111111e+50' ; execute my_insert using @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00 ; Warnings: -Warning 1265 Data truncated for column 'c1' at row 1 -Warning 1265 Data truncated for column 'c2' at row 1 -Warning 1265 Data truncated for column 'c3' at row 1 -Warning 1265 Data truncated for column 'c4' at row 1 -Warning 1265 Data truncated for column 'c5' at row 1 -Warning 1265 Data truncated for column 'c6' at row 1 +Warning 1264 Out of range value adjusted for column 'c1' at row 1 +Warning 1264 Out of range value adjusted for column 'c2' at row 1 +Warning 1264 Out of range value adjusted for column 'c3' at row 1 +Warning 1264 Out of range value adjusted for column 'c4' at row 1 +Warning 1264 Out of range value adjusted for column 'c5' at row 1 +Warning 1264 Out of range value adjusted for column 'c6' at row 1 Warning 1264 Out of range value adjusted for column 'c7' at row 1 Warning 1264 Out of range value adjusted for column 'c12' at row 1 execute my_select ; -c1 1 -c2 1 -c3 1 -c4 1 -c5 1 -c6 1 +c1 127 +c2 32767 +c3 8388607 +c4 2147483647 +c5 2147483647 +c6 9223372036854775807 c7 3.40282e+38 c8 1.11111111111111e+50 c9 1.11111111111111e+50 @@ -2739,21 +2739,21 @@ set @arg00= '-1.11111111111111111111e+50' ; execute my_insert using @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00 ; Warnings: -Warning 1265 Data truncated for column 'c1' at row 1 -Warning 1265 Data truncated for column 'c2' at row 1 -Warning 1265 Data truncated for column 'c3' at row 1 -Warning 1265 Data truncated for column 'c4' at row 1 -Warning 1265 Data truncated for column 'c5' at row 1 -Warning 1265 Data truncated for column 'c6' at row 1 +Warning 1264 Out of range value adjusted for column 'c1' at row 1 +Warning 1264 Out of range value adjusted for column 'c2' at row 1 +Warning 1264 Out of range value adjusted for column 'c3' at row 1 +Warning 1264 Out of range value adjusted for column 'c4' at row 1 +Warning 1264 Out of range value adjusted for column 'c5' at row 1 +Warning 1264 Out of range value adjusted for column 'c6' at row 1 Warning 1264 Out of range value adjusted for column 'c7' at row 1 Warning 1264 Out of range value adjusted for column 'c12' at row 1 execute my_select ; -c1 -1 -c2 -1 -c3 -1 -c4 -1 -c5 -1 -c6 -1 +c1 -128 +c2 -32768 +c3 -8388608 +c4 -2147483648 +c5 -2147483648 +c6 -9223372036854775808 c7 -3.40282e+38 c8 -1.11111111111111e+50 c9 -1.11111111111111e+50 diff --git a/mysql-test/r/ps_3innodb.result b/mysql-test/r/ps_3innodb.result index 2e7c4785542..88e8bf3ce04 100644 --- a/mysql-test/r/ps_3innodb.result +++ b/mysql-test/r/ps_3innodb.result @@ -2672,21 +2672,21 @@ set @arg00= '1.11111111111111111111e+50' ; execute my_insert using @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00 ; Warnings: -Warning 1265 Data truncated for column 'c1' at row 1 -Warning 1265 Data truncated for column 'c2' at row 1 -Warning 1265 Data truncated for column 'c3' at row 1 -Warning 1265 Data truncated for column 'c4' at row 1 -Warning 1265 Data truncated for column 'c5' at row 1 -Warning 1265 Data truncated for column 'c6' at row 1 +Warning 1264 Out of range value adjusted for column 'c1' at row 1 +Warning 1264 Out of range value adjusted for column 'c2' at row 1 +Warning 1264 Out of range value adjusted for column 'c3' at row 1 +Warning 1264 Out of range value adjusted for column 'c4' at row 1 +Warning 1264 Out of range value adjusted for column 'c5' at row 1 +Warning 1264 Out of range value adjusted for column 'c6' at row 1 Warning 1264 Out of range value adjusted for column 'c7' at row 1 Warning 1264 Out of range value adjusted for column 'c12' at row 1 execute my_select ; -c1 1 -c2 1 -c3 1 -c4 1 -c5 1 -c6 1 +c1 127 +c2 32767 +c3 8388607 +c4 2147483647 +c5 2147483647 +c6 9223372036854775807 c7 3.40282e+38 c8 1.11111111111111e+50 c9 1.11111111111111e+50 @@ -2722,21 +2722,21 @@ set @arg00= '-1.11111111111111111111e+50' ; execute my_insert using @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00 ; Warnings: -Warning 1265 Data truncated for column 'c1' at row 1 -Warning 1265 Data truncated for column 'c2' at row 1 -Warning 1265 Data truncated for column 'c3' at row 1 -Warning 1265 Data truncated for column 'c4' at row 1 -Warning 1265 Data truncated for column 'c5' at row 1 -Warning 1265 Data truncated for column 'c6' at row 1 +Warning 1264 Out of range value adjusted for column 'c1' at row 1 +Warning 1264 Out of range value adjusted for column 'c2' at row 1 +Warning 1264 Out of range value adjusted for column 'c3' at row 1 +Warning 1264 Out of range value adjusted for column 'c4' at row 1 +Warning 1264 Out of range value adjusted for column 'c5' at row 1 +Warning 1264 Out of range value adjusted for column 'c6' at row 1 Warning 1264 Out of range value adjusted for column 'c7' at row 1 Warning 1264 Out of range value adjusted for column 'c12' at row 1 execute my_select ; -c1 -1 -c2 -1 -c3 -1 -c4 -1 -c5 -1 -c6 -1 +c1 -128 +c2 -32768 +c3 -8388608 +c4 -2147483648 +c5 -2147483648 +c6 -9223372036854775808 c7 -3.40282e+38 c8 -1.11111111111111e+50 c9 -1.11111111111111e+50 diff --git a/mysql-test/r/ps_4heap.result b/mysql-test/r/ps_4heap.result index 8a0da364598..0e4c6fc3077 100644 --- a/mysql-test/r/ps_4heap.result +++ b/mysql-test/r/ps_4heap.result @@ -2673,21 +2673,21 @@ set @arg00= '1.11111111111111111111e+50' ; execute my_insert using @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00 ; Warnings: -Warning 1265 Data truncated for column 'c1' at row 1 -Warning 1265 Data truncated for column 'c2' at row 1 -Warning 1265 Data truncated for column 'c3' at row 1 -Warning 1265 Data truncated for column 'c4' at row 1 -Warning 1265 Data truncated for column 'c5' at row 1 -Warning 1265 Data truncated for column 'c6' at row 1 +Warning 1264 Out of range value adjusted for column 'c1' at row 1 +Warning 1264 Out of range value adjusted for column 'c2' at row 1 +Warning 1264 Out of range value adjusted for column 'c3' at row 1 +Warning 1264 Out of range value adjusted for column 'c4' at row 1 +Warning 1264 Out of range value adjusted for column 'c5' at row 1 +Warning 1264 Out of range value adjusted for column 'c6' at row 1 Warning 1264 Out of range value adjusted for column 'c7' at row 1 Warning 1264 Out of range value adjusted for column 'c12' at row 1 execute my_select ; -c1 1 -c2 1 -c3 1 -c4 1 -c5 1 -c6 1 +c1 127 +c2 32767 +c3 8388607 +c4 2147483647 +c5 2147483647 +c6 9223372036854775807 c7 3.40282e+38 c8 1.11111111111111e+50 c9 1.11111111111111e+50 @@ -2723,21 +2723,21 @@ set @arg00= '-1.11111111111111111111e+50' ; execute my_insert using @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00 ; Warnings: -Warning 1265 Data truncated for column 'c1' at row 1 -Warning 1265 Data truncated for column 'c2' at row 1 -Warning 1265 Data truncated for column 'c3' at row 1 -Warning 1265 Data truncated for column 'c4' at row 1 -Warning 1265 Data truncated for column 'c5' at row 1 -Warning 1265 Data truncated for column 'c6' at row 1 +Warning 1264 Out of range value adjusted for column 'c1' at row 1 +Warning 1264 Out of range value adjusted for column 'c2' at row 1 +Warning 1264 Out of range value adjusted for column 'c3' at row 1 +Warning 1264 Out of range value adjusted for column 'c4' at row 1 +Warning 1264 Out of range value adjusted for column 'c5' at row 1 +Warning 1264 Out of range value adjusted for column 'c6' at row 1 Warning 1264 Out of range value adjusted for column 'c7' at row 1 Warning 1264 Out of range value adjusted for column 'c12' at row 1 execute my_select ; -c1 -1 -c2 -1 -c3 -1 -c4 -1 -c5 -1 -c6 -1 +c1 -128 +c2 -32768 +c3 -8388608 +c4 -2147483648 +c5 -2147483648 +c6 -9223372036854775808 c7 -3.40282e+38 c8 -1.11111111111111e+50 c9 -1.11111111111111e+50 diff --git a/mysql-test/r/ps_5merge.result b/mysql-test/r/ps_5merge.result index 1c6e11f203c..1e337072ecb 100644 --- a/mysql-test/r/ps_5merge.result +++ b/mysql-test/r/ps_5merge.result @@ -2609,21 +2609,21 @@ set @arg00= '1.11111111111111111111e+50' ; execute my_insert using @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00 ; Warnings: -Warning 1265 Data truncated for column 'c1' at row 1 -Warning 1265 Data truncated for column 'c2' at row 1 -Warning 1265 Data truncated for column 'c3' at row 1 -Warning 1265 Data truncated for column 'c4' at row 1 -Warning 1265 Data truncated for column 'c5' at row 1 -Warning 1265 Data truncated for column 'c6' at row 1 +Warning 1264 Out of range value adjusted for column 'c1' at row 1 +Warning 1264 Out of range value adjusted for column 'c2' at row 1 +Warning 1264 Out of range value adjusted for column 'c3' at row 1 +Warning 1264 Out of range value adjusted for column 'c4' at row 1 +Warning 1264 Out of range value adjusted for column 'c5' at row 1 +Warning 1264 Out of range value adjusted for column 'c6' at row 1 Warning 1264 Out of range value adjusted for column 'c7' at row 1 Warning 1264 Out of range value adjusted for column 'c12' at row 1 execute my_select ; -c1 1 -c2 1 -c3 1 -c4 1 -c5 1 -c6 1 +c1 127 +c2 32767 +c3 8388607 +c4 2147483647 +c5 2147483647 +c6 9223372036854775807 c7 3.40282e+38 c8 1.11111111111111e+50 c9 1.11111111111111e+50 @@ -2659,21 +2659,21 @@ set @arg00= '-1.11111111111111111111e+50' ; execute my_insert using @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00 ; Warnings: -Warning 1265 Data truncated for column 'c1' at row 1 -Warning 1265 Data truncated for column 'c2' at row 1 -Warning 1265 Data truncated for column 'c3' at row 1 -Warning 1265 Data truncated for column 'c4' at row 1 -Warning 1265 Data truncated for column 'c5' at row 1 -Warning 1265 Data truncated for column 'c6' at row 1 +Warning 1264 Out of range value adjusted for column 'c1' at row 1 +Warning 1264 Out of range value adjusted for column 'c2' at row 1 +Warning 1264 Out of range value adjusted for column 'c3' at row 1 +Warning 1264 Out of range value adjusted for column 'c4' at row 1 +Warning 1264 Out of range value adjusted for column 'c5' at row 1 +Warning 1264 Out of range value adjusted for column 'c6' at row 1 Warning 1264 Out of range value adjusted for column 'c7' at row 1 Warning 1264 Out of range value adjusted for column 'c12' at row 1 execute my_select ; -c1 -1 -c2 -1 -c3 -1 -c4 -1 -c5 -1 -c6 -1 +c1 -128 +c2 -32768 +c3 -8388608 +c4 -2147483648 +c5 -2147483648 +c6 -9223372036854775808 c7 -3.40282e+38 c8 -1.11111111111111e+50 c9 -1.11111111111111e+50 @@ -5623,21 +5623,21 @@ set @arg00= '1.11111111111111111111e+50' ; execute my_insert using @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00 ; Warnings: -Warning 1265 Data truncated for column 'c1' at row 1 -Warning 1265 Data truncated for column 'c2' at row 1 -Warning 1265 Data truncated for column 'c3' at row 1 -Warning 1265 Data truncated for column 'c4' at row 1 -Warning 1265 Data truncated for column 'c5' at row 1 -Warning 1265 Data truncated for column 'c6' at row 1 +Warning 1264 Out of range value adjusted for column 'c1' at row 1 +Warning 1264 Out of range value adjusted for column 'c2' at row 1 +Warning 1264 Out of range value adjusted for column 'c3' at row 1 +Warning 1264 Out of range value adjusted for column 'c4' at row 1 +Warning 1264 Out of range value adjusted for column 'c5' at row 1 +Warning 1264 Out of range value adjusted for column 'c6' at row 1 Warning 1264 Out of range value adjusted for column 'c7' at row 1 Warning 1264 Out of range value adjusted for column 'c12' at row 1 execute my_select ; -c1 1 -c2 1 -c3 1 -c4 1 -c5 1 -c6 1 +c1 127 +c2 32767 +c3 8388607 +c4 2147483647 +c5 2147483647 +c6 9223372036854775807 c7 3.40282e+38 c8 1.11111111111111e+50 c9 1.11111111111111e+50 @@ -5673,21 +5673,21 @@ set @arg00= '-1.11111111111111111111e+50' ; execute my_insert using @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00 ; Warnings: -Warning 1265 Data truncated for column 'c1' at row 1 -Warning 1265 Data truncated for column 'c2' at row 1 -Warning 1265 Data truncated for column 'c3' at row 1 -Warning 1265 Data truncated for column 'c4' at row 1 -Warning 1265 Data truncated for column 'c5' at row 1 -Warning 1265 Data truncated for column 'c6' at row 1 +Warning 1264 Out of range value adjusted for column 'c1' at row 1 +Warning 1264 Out of range value adjusted for column 'c2' at row 1 +Warning 1264 Out of range value adjusted for column 'c3' at row 1 +Warning 1264 Out of range value adjusted for column 'c4' at row 1 +Warning 1264 Out of range value adjusted for column 'c5' at row 1 +Warning 1264 Out of range value adjusted for column 'c6' at row 1 Warning 1264 Out of range value adjusted for column 'c7' at row 1 Warning 1264 Out of range value adjusted for column 'c12' at row 1 execute my_select ; -c1 -1 -c2 -1 -c3 -1 -c4 -1 -c5 -1 -c6 -1 +c1 -128 +c2 -32768 +c3 -8388608 +c4 -2147483648 +c5 -2147483648 +c6 -9223372036854775808 c7 -3.40282e+38 c8 -1.11111111111111e+50 c9 -1.11111111111111e+50 diff --git a/mysql-test/r/ps_6bdb.result b/mysql-test/r/ps_6bdb.result index 3546b05870a..49e3f9d9bb7 100644 --- a/mysql-test/r/ps_6bdb.result +++ b/mysql-test/r/ps_6bdb.result @@ -2672,21 +2672,21 @@ set @arg00= '1.11111111111111111111e+50' ; execute my_insert using @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00 ; Warnings: -Warning 1265 Data truncated for column 'c1' at row 1 -Warning 1265 Data truncated for column 'c2' at row 1 -Warning 1265 Data truncated for column 'c3' at row 1 -Warning 1265 Data truncated for column 'c4' at row 1 -Warning 1265 Data truncated for column 'c5' at row 1 -Warning 1265 Data truncated for column 'c6' at row 1 +Warning 1264 Out of range value adjusted for column 'c1' at row 1 +Warning 1264 Out of range value adjusted for column 'c2' at row 1 +Warning 1264 Out of range value adjusted for column 'c3' at row 1 +Warning 1264 Out of range value adjusted for column 'c4' at row 1 +Warning 1264 Out of range value adjusted for column 'c5' at row 1 +Warning 1264 Out of range value adjusted for column 'c6' at row 1 Warning 1264 Out of range value adjusted for column 'c7' at row 1 Warning 1264 Out of range value adjusted for column 'c12' at row 1 execute my_select ; -c1 1 -c2 1 -c3 1 -c4 1 -c5 1 -c6 1 +c1 127 +c2 32767 +c3 8388607 +c4 2147483647 +c5 2147483647 +c6 9223372036854775807 c7 3.40282e+38 c8 1.11111111111111e+50 c9 1.11111111111111e+50 @@ -2722,21 +2722,21 @@ set @arg00= '-1.11111111111111111111e+50' ; execute my_insert using @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00 ; Warnings: -Warning 1265 Data truncated for column 'c1' at row 1 -Warning 1265 Data truncated for column 'c2' at row 1 -Warning 1265 Data truncated for column 'c3' at row 1 -Warning 1265 Data truncated for column 'c4' at row 1 -Warning 1265 Data truncated for column 'c5' at row 1 -Warning 1265 Data truncated for column 'c6' at row 1 +Warning 1264 Out of range value adjusted for column 'c1' at row 1 +Warning 1264 Out of range value adjusted for column 'c2' at row 1 +Warning 1264 Out of range value adjusted for column 'c3' at row 1 +Warning 1264 Out of range value adjusted for column 'c4' at row 1 +Warning 1264 Out of range value adjusted for column 'c5' at row 1 +Warning 1264 Out of range value adjusted for column 'c6' at row 1 Warning 1264 Out of range value adjusted for column 'c7' at row 1 Warning 1264 Out of range value adjusted for column 'c12' at row 1 execute my_select ; -c1 -1 -c2 -1 -c3 -1 -c4 -1 -c5 -1 -c6 -1 +c1 -128 +c2 -32768 +c3 -8388608 +c4 -2147483648 +c5 -2147483648 +c6 -9223372036854775808 c7 -3.40282e+38 c8 -1.11111111111111e+50 c9 -1.11111111111111e+50 diff --git a/mysql-test/r/ps_7ndb.result b/mysql-test/r/ps_7ndb.result index b1986ca62dc..c84cced15f5 100644 --- a/mysql-test/r/ps_7ndb.result +++ b/mysql-test/r/ps_7ndb.result @@ -2672,21 +2672,21 @@ set @arg00= '1.11111111111111111111e+50' ; execute my_insert using @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00 ; Warnings: -Warning 1265 Data truncated for column 'c1' at row 1 -Warning 1265 Data truncated for column 'c2' at row 1 -Warning 1265 Data truncated for column 'c3' at row 1 -Warning 1265 Data truncated for column 'c4' at row 1 -Warning 1265 Data truncated for column 'c5' at row 1 -Warning 1265 Data truncated for column 'c6' at row 1 +Warning 1264 Out of range value adjusted for column 'c1' at row 1 +Warning 1264 Out of range value adjusted for column 'c2' at row 1 +Warning 1264 Out of range value adjusted for column 'c3' at row 1 +Warning 1264 Out of range value adjusted for column 'c4' at row 1 +Warning 1264 Out of range value adjusted for column 'c5' at row 1 +Warning 1264 Out of range value adjusted for column 'c6' at row 1 Warning 1264 Out of range value adjusted for column 'c7' at row 1 Warning 1264 Out of range value adjusted for column 'c12' at row 1 execute my_select ; -c1 1 -c2 1 -c3 1 -c4 1 -c5 1 -c6 1 +c1 127 +c2 32767 +c3 8388607 +c4 2147483647 +c5 2147483647 +c6 9223372036854775807 c7 3.40282e+38 c8 1.11111111111111e+50 c9 1.11111111111111e+50 @@ -2722,21 +2722,21 @@ set @arg00= '-1.11111111111111111111e+50' ; execute my_insert using @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00, @arg00 ; Warnings: -Warning 1265 Data truncated for column 'c1' at row 1 -Warning 1265 Data truncated for column 'c2' at row 1 -Warning 1265 Data truncated for column 'c3' at row 1 -Warning 1265 Data truncated for column 'c4' at row 1 -Warning 1265 Data truncated for column 'c5' at row 1 -Warning 1265 Data truncated for column 'c6' at row 1 +Warning 1264 Out of range value adjusted for column 'c1' at row 1 +Warning 1264 Out of range value adjusted for column 'c2' at row 1 +Warning 1264 Out of range value adjusted for column 'c3' at row 1 +Warning 1264 Out of range value adjusted for column 'c4' at row 1 +Warning 1264 Out of range value adjusted for column 'c5' at row 1 +Warning 1264 Out of range value adjusted for column 'c6' at row 1 Warning 1264 Out of range value adjusted for column 'c7' at row 1 Warning 1264 Out of range value adjusted for column 'c12' at row 1 execute my_select ; -c1 -1 -c2 -1 -c3 -1 -c4 -1 -c5 -1 -c6 -1 +c1 -128 +c2 -32768 +c3 -8388608 +c4 -2147483648 +c5 -2147483648 +c6 -9223372036854775808 c7 -3.40282e+38 c8 -1.11111111111111e+50 c9 -1.11111111111111e+50 diff --git a/mysql-test/r/round.result b/mysql-test/r/round.result new file mode 100644 index 00000000000..e9a80df0f49 --- /dev/null +++ b/mysql-test/r/round.result @@ -0,0 +1,272 @@ +DROP TABLE IF EXISTS t1; +CREATE TABLE t1 (sint8 tinyint not null); +INSERT INTO t1 VALUES ('0.1'); +INSERT INTO t1 VALUES ('0.5'); +INSERT INTO t1 VALUES ('127.4'); +INSERT INTO t1 VALUES ('127.5'); +Warnings: +Warning 1264 Out of range value adjusted for column 'sint8' at row 1 +INSERT INTO t1 VALUES ('-0.1'); +INSERT INTO t1 VALUES ('-0.5'); +INSERT INTO t1 VALUES ('-127.4'); +INSERT INTO t1 VALUES ('-127.5'); +INSERT INTO t1 VALUES ('-128.4'); +INSERT INTO t1 VALUES ('-128.5'); +Warnings: +Warning 1264 Out of range value adjusted for column 'sint8' at row 1 +SELECT * FROM t1; +sint8 +0 +1 +127 +127 +0 +-1 +-127 +-128 +-128 +-128 +DROP TABLE t1; +CREATE TABLE t1 (uint8 tinyint unsigned not null); +INSERT INTO t1 VALUES ('0.1'); +INSERT INTO t1 VALUES ('0.5'); +INSERT INTO t1 VALUES ('127.4'); +INSERT INTO t1 VALUES ('127.5'); +INSERT INTO t1 VALUES ('-0.1'); +INSERT INTO t1 VALUES ('-0.5'); +Warnings: +Warning 1264 Out of range value adjusted for column 'uint8' at row 1 +INSERT INTO t1 VALUES ('255.4'); +INSERT INTO t1 VALUES ('255.5'); +Warnings: +Warning 1264 Out of range value adjusted for column 'uint8' at row 1 +SELECT * FROM t1; +uint8 +0 +1 +127 +128 +0 +0 +255 +255 +DROP TABLE t1; +CREATE TABLE t1 (sint16 smallint not null); +INSERT INTO t1 VALUES ('0.1'); +INSERT INTO t1 VALUES ('0.5'); +INSERT INTO t1 VALUES ('32767.4'); +INSERT INTO t1 VALUES ('32767.5'); +Warnings: +Warning 1264 Out of range value adjusted for column 'sint16' at row 1 +INSERT INTO t1 VALUES ('-0.1'); +INSERT INTO t1 VALUES ('-0.5'); +INSERT INTO t1 VALUES ('-32767.4'); +INSERT INTO t1 VALUES ('-32767.5'); +INSERT INTO t1 VALUES ('-32768.4'); +INSERT INTO t1 VALUES ('-32768.5'); +Warnings: +Warning 1264 Out of range value adjusted for column 'sint16' at row 1 +SELECT * FROM t1; +sint16 +0 +1 +32767 +32767 +0 +-1 +-32767 +-32768 +-32768 +-32768 +DROP TABLE t1; +CREATE TABLE t1 (uint16 smallint unsigned not null); +INSERT INTO t1 VALUES ('0.1'); +INSERT INTO t1 VALUES ('0.5'); +INSERT INTO t1 VALUES ('32767.4'); +INSERT INTO t1 VALUES ('32767.5'); +INSERT INTO t1 VALUES ('-0.1'); +INSERT INTO t1 VALUES ('-0.5'); +Warnings: +Warning 1264 Out of range value adjusted for column 'uint16' at row 1 +INSERT INTO t1 VALUES ('65535.4'); +INSERT INTO t1 VALUES ('65535.5'); +Warnings: +Warning 1264 Out of range value adjusted for column 'uint16' at row 1 +SELECT * FROM t1; +uint16 +0 +1 +32767 +32768 +0 +0 +65535 +65535 +DROP TABLE t1; +CREATE TABLE t1 (sint24 mediumint not null); +INSERT INTO t1 VALUES ('0.1'); +INSERT INTO t1 VALUES ('0.5'); +INSERT INTO t1 VALUES ('8388607.4'); +INSERT INTO t1 VALUES ('8388607.5'); +Warnings: +Warning 1264 Out of range value adjusted for column 'sint24' at row 1 +INSERT INTO t1 VALUES ('-0.1'); +INSERT INTO t1 VALUES ('-0.5'); +INSERT INTO t1 VALUES ('-8388607.4'); +INSERT INTO t1 VALUES ('-8388607.5'); +INSERT INTO t1 VALUES ('-8388608.4'); +INSERT INTO t1 VALUES ('-8388608.5'); +Warnings: +Warning 1264 Out of range value adjusted for column 'sint24' at row 1 +SELECT * FROM t1; +sint24 +0 +1 +8388607 +8388607 +0 +-1 +-8388607 +-8388608 +-8388608 +-8388608 +DROP TABLE t1; +CREATE TABLE t1 (uint24 mediumint unsigned not null); +INSERT INTO t1 VALUES ('0.1'); +INSERT INTO t1 VALUES ('0.5'); +INSERT INTO t1 VALUES ('8388607.4'); +INSERT INTO t1 VALUES ('8388607.5'); +INSERT INTO t1 VALUES ('-0.1'); +INSERT INTO t1 VALUES ('-0.5'); +Warnings: +Warning 1264 Out of range value adjusted for column 'uint24' at row 1 +INSERT INTO t1 VALUES ('16777215.4'); +INSERT INTO t1 VALUES ('16777215.5'); +Warnings: +Warning 1264 Out of range value adjusted for column 'uint24' at row 1 +SELECT * FROM t1; +uint24 +0 +1 +8388607 +8388608 +0 +0 +16777215 +16777215 +DROP TABLE t1; +CREATE TABLE t1 (sint64 bigint not null); +INSERT INTO t1 VALUES ('0.1'); +INSERT INTO t1 VALUES ('0.5'); +INSERT INTO t1 VALUES ('9223372036854775807.4'); +INSERT INTO t1 VALUES ('9223372036854775807.5'); +Warnings: +Warning 1264 Out of range value adjusted for column 'sint64' at row 1 +INSERT INTO t1 VALUES ('-0.1'); +INSERT INTO t1 VALUES ('-0.5'); +INSERT INTO t1 VALUES ('-9223372036854775807.4'); +INSERT INTO t1 VALUES ('-9223372036854775807.5'); +INSERT INTO t1 VALUES ('-9223372036854775808.4'); +INSERT INTO t1 VALUES ('-9223372036854775808.5'); +Warnings: +Warning 1264 Out of range value adjusted for column 'sint64' at row 1 +SELECT * FROM t1; +sint64 +0 +1 +9223372036854775807 +9223372036854775807 +0 +-1 +-9223372036854775807 +-9223372036854775808 +-9223372036854775808 +-9223372036854775808 +DROP TABLE t1; +CREATE TABLE t1 (uint64 bigint unsigned not null); +INSERT INTO t1 VALUES ('0.1'); +INSERT INTO t1 VALUES ('0.5'); +INSERT INTO t1 VALUES ('9223372036854775807.4'); +INSERT INTO t1 VALUES ('9223372036854775807.5'); +INSERT INTO t1 VALUES ('-0.1'); +INSERT INTO t1 VALUES ('-0.5'); +Warnings: +Warning 1264 Out of range value adjusted for column 'uint64' at row 1 +INSERT INTO t1 VALUES ('18446744073709551615.4'); +INSERT INTO t1 VALUES ('18446744073709551615.5'); +Warnings: +Warning 1264 Out of range value adjusted for column 'uint64' at row 1 +INSERT INTO t1 VALUES ('1844674407370955161.0'); +INSERT INTO t1 VALUES ('1844674407370955161.1'); +INSERT INTO t1 VALUES ('1844674407370955161.2'); +INSERT INTO t1 VALUES ('1844674407370955161.3'); +INSERT INTO t1 VALUES ('1844674407370955161.4'); +INSERT INTO t1 VALUES ('1844674407370955161.5'); +INSERT INTO t1 VALUES ('1844674407370955161.0e1'); +INSERT INTO t1 VALUES ('1844674407370955161.1e1'); +INSERT INTO t1 VALUES ('1844674407370955161.2e1'); +INSERT INTO t1 VALUES ('1844674407370955161.3e1'); +INSERT INTO t1 VALUES ('1844674407370955161.4e1'); +INSERT INTO t1 VALUES ('1844674407370955161.5e1'); +INSERT INTO t1 VALUES ('18446744073709551610e-1'); +INSERT INTO t1 VALUES ('18446744073709551611e-1'); +INSERT INTO t1 VALUES ('18446744073709551612e-1'); +INSERT INTO t1 VALUES ('18446744073709551613e-1'); +INSERT INTO t1 VALUES ('18446744073709551614e-1'); +INSERT INTO t1 VALUES ('18446744073709551615e-1'); +SELECT * FROM t1; +uint64 +0 +1 +9223372036854775807 +9223372036854775808 +0 +0 +18446744073709551615 +18446744073709551615 +1844674407370955161 +1844674407370955161 +1844674407370955161 +1844674407370955161 +1844674407370955161 +1844674407370955162 +18446744073709551610 +18446744073709551611 +18446744073709551612 +18446744073709551613 +18446744073709551614 +18446744073709551615 +1844674407370955161 +1844674407370955161 +1844674407370955161 +1844674407370955161 +1844674407370955161 +1844674407370955162 +DROP TABLE t1; +CREATE TABLE t1 (str varchar(128), sint64 bigint not null default 0); +INSERT INTO t1 (str) VALUES ('1.5'); +INSERT INTO t1 (str) VALUES ('1.00005e4'); +INSERT INTO t1 (str) VALUES ('1.0005e3'); +INSERT INTO t1 (str) VALUES ('1.005e2'); +INSERT INTO t1 (str) VALUES ('1.05e1'); +INSERT INTO t1 (str) VALUES ('1.5e0'); +INSERT INTO t1 (str) VALUES ('100005e-1'); +INSERT INTO t1 (str) VALUES ('100050e-2'); +INSERT INTO t1 (str) VALUES ('100500e-3'); +INSERT INTO t1 (str) VALUES ('105000e-4'); +INSERT INTO t1 (str) VALUES ('150000e-5'); +UPDATE t1 SET sint64=str; +SELECT * FROM t1; +str sint64 +1.5 2 +1.00005e4 10001 +1.0005e3 1001 +1.005e2 101 +1.05e1 11 +1.5e0 2 +100005e-1 10001 +100050e-2 1001 +100500e-3 101 +105000e-4 11 +150000e-5 2 +DROP TABLE t1; diff --git a/mysql-test/r/rpl_rewrite_db.result b/mysql-test/r/rpl_rewrite_db.result index 71ac39010b5..1b843bffdca 100644 --- a/mysql-test/r/rpl_rewrite_db.result +++ b/mysql-test/r/rpl_rewrite_db.result @@ -67,9 +67,9 @@ drop table t1; create table t1 (a int, b char(10)); load data infile '../std_data_ln/loaddata3.dat' into table t1 fields terminated by '' enclosed by '' ignore 1 lines; Warnings: -Warning 1264 Out of range value adjusted for column 'a' at row 3 +Warning 1366 Incorrect integer value: 'error ' for column 'a' at row 3 Warning 1262 Row 3 was truncated; it contained more data than there were input columns -Warning 1264 Out of range value adjusted for column 'a' at row 5 +Warning 1366 Incorrect integer value: 'wrong end ' for column 'a' at row 5 Warning 1262 Row 5 was truncated; it contained more data than there were input columns select * from rewrite.t1; a b @@ -81,7 +81,8 @@ a b truncate table t1; load data infile '../std_data_ln/loaddata4.dat' into table t1 fields terminated by '' enclosed by '' lines terminated by '' ignore 1 lines; Warnings: -Warning 1264 Out of range value adjusted for column 'a' at row 4 +Warning 1366 Incorrect integer value: ' +' for column 'a' at row 4 Warning 1261 Row 4 doesn't contain data for all columns select * from rewrite.t1; a b diff --git a/mysql-test/r/select.result b/mysql-test/r/select.result index 0c62d3f570f..543dfd82eae 100644 --- a/mysql-test/r/select.result +++ b/mysql-test/r/select.result @@ -2734,7 +2734,7 @@ CREATE TABLE t1 (i BIGINT UNSIGNED NOT NULL); INSERT INTO t1 VALUES (10); SELECT i='1e+01',i=1e+01, i in (1e+01,1e+01), i in ('1e+01','1e+01') FROM t1; i='1e+01' i=1e+01 i in (1e+01,1e+01) i in ('1e+01','1e+01') -0 1 1 1 +1 1 1 1 DROP TABLE t1; CREATE TABLE t1 (a int, b int); INSERT INTO t1 VALUES (1,1), (2,1), (4,10); diff --git a/mysql-test/r/sp-vars.result b/mysql-test/r/sp-vars.result index 83ee188bfa4..14040f8420e 100644 --- a/mysql-test/r/sp-vars.result +++ b/mysql-test/r/sp-vars.result @@ -896,7 +896,7 @@ sp_var @user_var 0 Warnings: -Warning 1264 Out of range value adjusted for column 'sp_var' at row 1 +Warning 1366 Incorrect integer value: 'Hello, world!' for column 'sp_var' at row 1 DROP PROCEDURE p1; DROP TABLE t1; diff --git a/mysql-test/r/strict.result b/mysql-test/r/strict.result index e144eed92f5..702fc68bb25 100644 --- a/mysql-test/r/strict.result +++ b/mysql-test/r/strict.result @@ -619,9 +619,9 @@ ERROR 22012: Division by 0 UPDATE t1 SET col1= MOD(col1,0) WHERE col1 > 0; ERROR 22012: Division by 0 INSERT INTO t1 (col1) VALUES (''); -ERROR 22003: Out of range value adjusted for column 'col1' at row 1 +ERROR HY000: Incorrect integer value: '' for column 'col1' at row 1 INSERT INTO t1 (col1) VALUES ('a59b'); -ERROR 22003: Out of range value adjusted for column 'col1' at row 1 +ERROR HY000: Incorrect integer value: 'a59b' for column 'col1' at row 1 INSERT INTO t1 (col1) VALUES ('1a'); ERROR 01000: Data truncated for column 'col1' at row 1 INSERT IGNORE INTO t1 (col1) VALUES ('2a'); @@ -701,9 +701,9 @@ ERROR 22012: Division by 0 UPDATE t1 SET col1= MOD(col1,0) WHERE col1 > 0; ERROR 22012: Division by 0 INSERT INTO t1 (col1) VALUES (''); -ERROR 22003: Out of range value adjusted for column 'col1' at row 1 +ERROR HY000: Incorrect integer value: '' for column 'col1' at row 1 INSERT INTO t1 (col1) VALUES ('a59b'); -ERROR 22003: Out of range value adjusted for column 'col1' at row 1 +ERROR HY000: Incorrect integer value: 'a59b' for column 'col1' at row 1 INSERT INTO t1 (col1) VALUES ('1a'); ERROR 01000: Data truncated for column 'col1' at row 1 INSERT IGNORE INTO t1 (col1) VALUES ('2a'); @@ -925,10 +925,10 @@ Warning 1264 Out of range value adjusted for column 'col2' at row 1 Warning 1264 Out of range value adjusted for column 'col2' at row 1 SELECT * FROM t1; col1 col2 -0 0 +-2.2e-307 0 1e-303 0 1.7e+308 1.7e+308 -0 0 +-2.2e-307 0 -2e-307 0 1.7e+308 1.7e+308 0 NULL diff --git a/mysql-test/r/type_bit.result b/mysql-test/r/type_bit.result index f0ac00cedfa..bd58e83bb3f 100644 --- a/mysql-test/r/type_bit.result +++ b/mysql-test/r/type_bit.result @@ -602,4 +602,12 @@ NULL NULL 0 0 11111111 11111111 drop table bug15583; +create table t1(a bit(1), b smallint unsigned); +insert into t1 (b, a) values ('2', '1'); +Warnings: +Warning 1264 Out of range value adjusted for column 'a' at row 1 +select hex(a), b from t1; +hex(a) b +1 2 +drop table t1; End of 5.0 tests diff --git a/mysql-test/r/type_float.result b/mysql-test/r/type_float.result index 61482ab282c..6790ae2c67d 100644 --- a/mysql-test/r/type_float.result +++ b/mysql-test/r/type_float.result @@ -262,6 +262,13 @@ desc t3; Field Type Null Key Default Extra a decimal(21,2) NO 0.00 drop table t1,t2,t3; +select 1e-308, 1.00000001e-300, 100000000e-300; +1e-308 1.00000001e-300 100000000e-300 +0 1.00000001e-300 1e-292 +select 10e307; +10e307 +1e+308 +End of 4.1 tests create table t1 (s1 float(0,2)); ERROR 42000: For float(M,D), double(M,D) or decimal(M,D), M must be >= D (column 's1'). create table t1 (s1 float(1,2)); diff --git a/mysql-test/r/view.result b/mysql-test/r/view.result index 6364002993f..213a1dcde20 100644 --- a/mysql-test/r/view.result +++ b/mysql-test/r/view.result @@ -1306,9 +1306,9 @@ a b delete from t1; load data infile '../std_data_ln/loaddata3.dat' ignore into table v1 fields terminated by '' enclosed by '' ignore 1 lines; Warnings: -Warning 1264 Out of range value adjusted for column 'a' at row 3 +Warning 1366 Incorrect integer value: 'error ' for column 'a' at row 3 Error 1369 CHECK OPTION failed 'test.v1' -Warning 1264 Out of range value adjusted for column 'a' at row 4 +Warning 1366 Incorrect integer value: 'wrong end ' for column 'a' at row 4 Error 1369 CHECK OPTION failed 'test.v1' select * from t1; a b diff --git a/mysql-test/r/warnings.result b/mysql-test/r/warnings.result index 283a0661721..d0ad4ca6648 100644 --- a/mysql-test/r/warnings.result +++ b/mysql-test/r/warnings.result @@ -31,19 +31,19 @@ Error 1064 You have an error in your SQL syntax; check the manual that correspon insert into t1 values (1); insert into t1 values ("hej"); Warnings: -Warning 1264 Out of range value adjusted for column 'a' at row 1 +Warning 1366 Incorrect integer value: 'hej' for column 'a' at row 1 insert into t1 values ("hej"),("då"); Warnings: -Warning 1264 Out of range value adjusted for column 'a' at row 1 -Warning 1264 Out of range value adjusted for column 'a' at row 2 +Warning 1366 Incorrect integer value: 'hej' for column 'a' at row 1 +Warning 1366 Incorrect integer value: 'd?' for column 'a' at row 2 set SQL_WARNINGS=1; insert into t1 values ("hej"); Warnings: -Warning 1264 Out of range value adjusted for column 'a' at row 1 +Warning 1366 Incorrect integer value: 'hej' for column 'a' at row 1 insert into t1 values ("hej"),("då"); Warnings: -Warning 1264 Out of range value adjusted for column 'a' at row 1 -Warning 1264 Out of range value adjusted for column 'a' at row 2 +Warning 1366 Incorrect integer value: 'hej' for column 'a' at row 1 +Warning 1366 Incorrect integer value: 'd?' for column 'a' at row 2 drop table t1; set SQL_WARNINGS=0; drop temporary table if exists not_exists; @@ -194,44 +194,44 @@ create table t1 (a int); insert into t1 (a) values (1), (2), (3), (4), (5), (6), (7), (8), (9), (10); update t1 set a='abc'; Warnings: -Warning 1264 Out of range value adjusted for column 'a' at row 1 -Warning 1264 Out of range value adjusted for column 'a' at row 2 -Warning 1264 Out of range value adjusted for column 'a' at row 3 -Warning 1264 Out of range value adjusted for column 'a' at row 4 -Warning 1264 Out of range value adjusted for column 'a' at row 5 -Warning 1264 Out of range value adjusted for column 'a' at row 6 -Warning 1264 Out of range value adjusted for column 'a' at row 7 -Warning 1264 Out of range value adjusted for column 'a' at row 8 -Warning 1264 Out of range value adjusted for column 'a' at row 9 -Warning 1264 Out of range value adjusted for column 'a' at row 10 +Warning 1366 Incorrect integer value: 'abc' for column 'a' at row 1 +Warning 1366 Incorrect integer value: 'abc' for column 'a' at row 2 +Warning 1366 Incorrect integer value: 'abc' for column 'a' at row 3 +Warning 1366 Incorrect integer value: 'abc' for column 'a' at row 4 +Warning 1366 Incorrect integer value: 'abc' for column 'a' at row 5 +Warning 1366 Incorrect integer value: 'abc' for column 'a' at row 6 +Warning 1366 Incorrect integer value: 'abc' for column 'a' at row 7 +Warning 1366 Incorrect integer value: 'abc' for column 'a' at row 8 +Warning 1366 Incorrect integer value: 'abc' for column 'a' at row 9 +Warning 1366 Incorrect integer value: 'abc' for column 'a' at row 10 show warnings limit 2, 1; Level Code Message -Warning 1264 Out of range value adjusted for column 'a' at row 3 +Warning 1366 Incorrect integer value: 'abc' for column 'a' at row 3 show warnings limit 0, 10; Level Code Message -Warning 1264 Out of range value adjusted for column 'a' at row 1 -Warning 1264 Out of range value adjusted for column 'a' at row 2 -Warning 1264 Out of range value adjusted for column 'a' at row 3 -Warning 1264 Out of range value adjusted for column 'a' at row 4 -Warning 1264 Out of range value adjusted for column 'a' at row 5 -Warning 1264 Out of range value adjusted for column 'a' at row 6 -Warning 1264 Out of range value adjusted for column 'a' at row 7 -Warning 1264 Out of range value adjusted for column 'a' at row 8 -Warning 1264 Out of range value adjusted for column 'a' at row 9 -Warning 1264 Out of range value adjusted for column 'a' at row 10 +Warning 1366 Incorrect integer value: 'abc' for column 'a' at row 1 +Warning 1366 Incorrect integer value: 'abc' for column 'a' at row 2 +Warning 1366 Incorrect integer value: 'abc' for column 'a' at row 3 +Warning 1366 Incorrect integer value: 'abc' for column 'a' at row 4 +Warning 1366 Incorrect integer value: 'abc' for column 'a' at row 5 +Warning 1366 Incorrect integer value: 'abc' for column 'a' at row 6 +Warning 1366 Incorrect integer value: 'abc' for column 'a' at row 7 +Warning 1366 Incorrect integer value: 'abc' for column 'a' at row 8 +Warning 1366 Incorrect integer value: 'abc' for column 'a' at row 9 +Warning 1366 Incorrect integer value: 'abc' for column 'a' at row 10 show warnings limit 9, 1; Level Code Message -Warning 1264 Out of range value adjusted for column 'a' at row 10 +Warning 1366 Incorrect integer value: 'abc' for column 'a' at row 10 show warnings limit 10, 1; Level Code Message show warnings limit 9, 2; Level Code Message -Warning 1264 Out of range value adjusted for column 'a' at row 10 +Warning 1366 Incorrect integer value: 'abc' for column 'a' at row 10 show warnings limit 0, 0; Level Code Message show warnings limit 1; Level Code Message -Warning 1264 Out of range value adjusted for column 'a' at row 1 +Warning 1366 Incorrect integer value: 'abc' for column 'a' at row 1 show warnings limit 0; Level Code Message show warnings limit 1, 0; @@ -243,3 +243,59 @@ a select * from t1 limit 0, 0; a drop table t1; +End of 4.1 tests +CREATE TABLE t1( f1 CHAR(20) ); +CREATE TABLE t2( f1 CHAR(20), f2 CHAR(25) ); +CREATE TABLE t3( f1 CHAR(20), f2 CHAR(25), f3 DATE ); +INSERT INTO t1 VALUES ( 'a`' ); +INSERT INTO t2 VALUES ( 'a`', 'a`' ); +INSERT INTO t3 VALUES ( 'a`', 'a`', '1000-01-1' ); +DROP PROCEDURE IF EXISTS sp1; +Warnings: +Note 1305 PROCEDURE sp1 does not exist +DROP PROCEDURE IF EXISTS sp2; +Warnings: +Note 1305 PROCEDURE sp2 does not exist +DROP PROCEDURE IF EXISTS sp3; +Warnings: +Note 1305 PROCEDURE sp3 does not exist +CREATE PROCEDURE sp1() +BEGIN +DECLARE x NUMERIC ZEROFILL; +SELECT f1 INTO x FROM t1 LIMIT 1; +END// +CREATE PROCEDURE sp2() +BEGIN +DECLARE x NUMERIC ZEROFILL; +SELECT f1 INTO x FROM t2 LIMIT 1; +END// +CREATE PROCEDURE sp3() +BEGIN +DECLARE x NUMERIC ZEROFILL; +SELECT f1 INTO x FROM t3 LIMIT 1; +END// +CALL sp1(); +Warnings: +Warning 1366 Incorrect decimal value: 'a`' for column 'x' at row 1 +CALL sp2(); +Warnings: +Warning 1366 Incorrect decimal value: 'a`' for column 'x' at row 1 +CALL sp3(); +Warnings: +Warning 1366 Incorrect decimal value: 'a`' for column 'x' at row 1 +DROP PROCEDURE IF EXISTS sp1; +CREATE PROCEDURE sp1() +BEGIN +declare x numeric unsigned zerofill; +SELECT f1 into x from t2 limit 1; +END// +CALL sp1(); +Warnings: +Warning 1366 Incorrect decimal value: 'a`' for column 'x' at row 1 +DROP TABLE t1; +DROP TABLE t2; +DROP TABLE t3; +DROP PROCEDURE sp1; +DROP PROCEDURE sp2; +DROP PROCEDURE sp3; +End of 5.0 tests diff --git a/mysql-test/t/analyse.test b/mysql-test/t/analyse.test index a248c671c18..efcf5f6421c 100644 --- a/mysql-test/t/analyse.test +++ b/mysql-test/t/analyse.test @@ -90,5 +90,16 @@ create table t2 (country_id int primary key, country char(20) not null); insert into t2 values (1, 'USA'),(2,'India'), (3,'Finland'); select product, sum(profit),avg(profit) from t1 group by product with rollup procedure analyse(); drop table t1,t2; -# End of 4.1 tests +# +# Bug #20305 PROCEDURE ANALYSE() returns wrong M for FLOAT(M, D) and DOUBLE(M, D) +# + +create table t1 (f1 double(10,5), f2 char(10), f3 double(10,5)); +insert into t1 values (5.999, "5.9999", 5.99999), (9.555, "9.5555", 9.55555); +select f1 from t1 procedure analyse(1, 1); +select f2 from t1 procedure analyse(1, 1); +select f3 from t1 procedure analyse(1, 1); +drop table t1; + +--echo End of 4.1 tests diff --git a/mysql-test/t/ctype_gbk.test b/mysql-test/t/ctype_gbk.test index 7aec48586d8..5ff138fa97b 100644 --- a/mysql-test/t/ctype_gbk.test +++ b/mysql-test/t/ctype_gbk.test @@ -42,3 +42,13 @@ DROP TABLE t1; select hex(convert(_gbk 0xA14041 using ucs2)); # End of 4.1 tests + +# +# Bug#21620 ALTER TABLE affects other columns +# +create table t1 (c1 text not null, c2 text not null) character set gbk; +alter table t1 change c1 c1 mediumtext character set gbk not null; +show create table t1; +drop table t1; + +--echo End of 5.0 tests diff --git a/mysql-test/t/ctype_utf8.test b/mysql-test/t/ctype_utf8.test index 39928f18f2e..5dc3e6d5eb2 100644 --- a/mysql-test/t/ctype_utf8.test +++ b/mysql-test/t/ctype_utf8.test @@ -1069,6 +1069,16 @@ explain select a from t1 group by a; select a from t1 group by a; drop table t1; +# +# Bug #20204: "order by" changes the results returned +# + +create table t1(a char(10)) default charset utf8; +insert into t1 values ('123'), ('456'); +explain + select substr(Z.a,-1), Z.a from t1 as Y join t1 as Z on Y.a=Z.a order by 1; +select substr(Z.a,-1), Z.a from t1 as Y join t1 as Z on Y.a=Z.a order by 1; +drop table t1; # End of 4.1 tests # @@ -1147,3 +1157,23 @@ execute my_stmt using @a; set @a:=null; execute my_stmt using @a; drop table if exists t1; + +# +# Bug#19960: Inconsistent results when joining +# InnoDB tables using partial UTF8 indexes +# +CREATE TABLE t1 ( + colA int(11) NOT NULL, + colB varchar(255) character set utf8 NOT NULL, + PRIMARY KEY (colA) +) ENGINE=InnoDB DEFAULT CHARSET=latin1; +INSERT INTO t1 (colA, colB) VALUES (1, 'foo'), (2, 'foo bar'); +CREATE TABLE t2 ( + colA int(11) NOT NULL, + colB varchar(255) character set utf8 NOT NULL, + KEY bad (colA,colB(3)) +) ENGINE=InnoDB DEFAULT CHARSET=latin1; +INSERT INTO t2 (colA, colB) VALUES (1, 'foo'),(2, 'foo bar'); +SELECT * FROM t1 JOIN t2 ON t1.colA=t2.colA AND t1.colB=t2.colB +WHERE t1.colA < 3; +DROP TABLE t1, t2; diff --git a/mysql-test/t/execution_constants.test b/mysql-test/t/execution_constants.test new file mode 100644 index 00000000000..00967b2eeba --- /dev/null +++ b/mysql-test/t/execution_constants.test @@ -0,0 +1,74 @@ +# +# Bug#21476: Lost Database Connection During Query +# +# When the amount of stack space we think we need to report an error is +# actually too small, then we can get SEGVs. But, we don't want to reserve +# space that we could use to get real work done. So, we want the reserved +# space small, and this test verifies that the reservation is not too small. + +CREATE TABLE `t_bug21476` ( + `ID_BOARD` smallint(5) unsigned NOT NULL default '0', + `ID_MEMBER` mediumint(8) unsigned NOT NULL default '0', + `logTime` int(10) unsigned NOT NULL default '0', + `ID_MSG` mediumint(8) unsigned NOT NULL default '0', + PRIMARY KEY (`ID_MEMBER`,`ID_BOARD`), + KEY `logTime` (`logTime`) +) ENGINE=MyISAM DEFAULT CHARSET=cp1251 COLLATE=cp1251_bulgarian_ci; + +INSERT INTO `t_bug21476` VALUES (2,2,1154870939,0),(1,2,1154870957,0),(2,183,1154941362,0),(2,84,1154904301,0),(1,84,1154905867,0),(2,13,1154947484,10271),(3,84,1154880549,0),(1,6,1154892183,0),(2,25,1154947581,10271),(3,25,1154904760,0),(1,25,1154947373,10271),(1,179,1154899992,0),(2,179,1154899410,0),(5,25,1154901666,0),(2,329,1154902026,0),(3,329,1154902040,0),(1,329,1154902058,0),(1,13,1154930841,0),(3,85,1154904987,0),(1,183,1154929665,0),(3,13,1154931268,0),(1,85,1154936888,0),(1,169,1154937959,0),(2,169,1154941717,0),(3,183,1154939810,0),(3,169,1154941734,0); + +delimiter //; +let $query_head=UPDATE t_bug21476 SET ID_MSG = IF(logTime BETWEEN 1 AND 1101770053, 2, // +let $query_tail =) WHERE logTime BETWEEN 1 AND 1104091539 AND ID_MSG = 0// + +# Scan over the possible stack heights, trying to recurse to exactly that +# depth. Eventually, we will reach our imposed limit on height and try to +# raise an error. If the remaining stack space is enough to raise that error, +# we will get an error-number of 1436 and quit the loop. If it's not enough +# space, we should get a SEGV + +# Well more than enough recursions to find the end of our stack. +let $i = 100000// +disable_query_log// +disable_result_log// +while ($i) +{ + # If we SEGV because the min stack size is exceeded, this would return error + # 2013 . + error 0,1436 // + eval $query_head 0 $query_tail// + + if ($mysql_errno != 1436) + { + # We reached the place where we reported an error about the stack limit, + # and we successfully returned the error. That means that at the stack + # limit, we still have enough space reserved to report an error. + let $i = 1// + } + + # Multiplying by three stack frames should be fine enough resolution. + # Trading exactness for speed. + + # go one more level deep + let $query_head = $query_head IF(logTime <= 1104091$i, $i, // + let $query_tail =) $query_tail// + + # go one more level deep + let $query_head = $query_head IF(logTime <= 1105091$i, $i, // + let $query_tail =) $query_tail// + + # go one more level deep + let $query_head = $query_head IF(logTime <= 1106091$i, $i, // + let $query_tail =) $query_tail// + + dec $i// +} +enable_result_log// +enable_query_log// + +echo Assertion: mysql_errno 1436 == $mysql_errno// + +delimiter ;// +DROP TABLE `t_bug21476`; + +--echo End of 5.0 tests. diff --git a/mysql-test/t/func_time.test b/mysql-test/t/func_time.test index 7303be31e03..2b3fb86829d 100644 --- a/mysql-test/t/func_time.test +++ b/mysql-test/t/func_time.test @@ -447,6 +447,25 @@ show create table t1; drop table t1; # +# 21913: DATE_FORMAT() Crashes mysql server if I use it through +# mysql-connector-j driver. +# + +SET NAMES latin1; +SET character_set_results = NULL; +SHOW VARIABLES LIKE 'character_set_results'; + +CREATE TABLE testBug8868 (field1 DATE, field2 VARCHAR(32) CHARACTER SET BINARY); +INSERT INTO testBug8868 VALUES ('2006-09-04', 'abcd'); + +SELECT DATE_FORMAT(field1,'%b-%e %l:%i%p') as fmtddate, field2 FROM testBug8868; + +DROP TABLE testBug8868; + +SET NAMES DEFAULT; + + +# # Bug #19844 time_format in Union truncates values # diff --git a/mysql-test/t/lowercase_fs_off.test b/mysql-test/t/lowercase_fs_off.test index 7f7b573e7ee..883315994fe 100644 --- a/mysql-test/t/lowercase_fs_off.test +++ b/mysql-test/t/lowercase_fs_off.test @@ -3,6 +3,7 @@ # i.e. lower_case_filesystem=OFF # -- source include/have_case_sensitive_file_system.inc +-- source include/not_embedded.inc connect (master,localhost,root,,); connection master; diff --git a/mysql-test/t/mysqltest.test b/mysql-test/t/mysqltest.test index 6a0b805f43b..c30af8c8f26 100644 --- a/mysql-test/t/mysqltest.test +++ b/mysql-test/t/mysqltest.test @@ -507,9 +507,21 @@ echo $where2; let $where3=a long $where variable content; echo $where3; +let $where3=a long \\\$where variable content; +echo $where3; + let $novar1= $novar2; echo $novar1; +let $cat=na; +let $cat=ba$cat$cat; +echo banana = $cat; + +# ba\$cat\$cat should have been sufficient. +# ba\\\$cat\\\$cat -> ba\$cat\$cat -> ba$cat$cat -> banana +# Magnus' upcoming patch will fix the missing second interpretation. +let $cat=ba\\\$cat\\\$cat; +echo Not a banana: $cat; # Test illegal uses of let diff --git a/mysql-test/t/round.test b/mysql-test/t/round.test new file mode 100644 index 00000000000..d018fa7e34e --- /dev/null +++ b/mysql-test/t/round.test @@ -0,0 +1,145 @@ +--disable_warnings +DROP TABLE IF EXISTS t1; +--enable_warnings + +CREATE TABLE t1 (sint8 tinyint not null); +INSERT INTO t1 VALUES ('0.1'); +INSERT INTO t1 VALUES ('0.5'); +INSERT INTO t1 VALUES ('127.4'); +INSERT INTO t1 VALUES ('127.5'); +INSERT INTO t1 VALUES ('-0.1'); +INSERT INTO t1 VALUES ('-0.5'); +INSERT INTO t1 VALUES ('-127.4'); +INSERT INTO t1 VALUES ('-127.5'); +INSERT INTO t1 VALUES ('-128.4'); +INSERT INTO t1 VALUES ('-128.5'); +SELECT * FROM t1; +DROP TABLE t1; + +CREATE TABLE t1 (uint8 tinyint unsigned not null); +INSERT INTO t1 VALUES ('0.1'); +INSERT INTO t1 VALUES ('0.5'); +INSERT INTO t1 VALUES ('127.4'); +INSERT INTO t1 VALUES ('127.5'); +INSERT INTO t1 VALUES ('-0.1'); +INSERT INTO t1 VALUES ('-0.5'); +INSERT INTO t1 VALUES ('255.4'); +INSERT INTO t1 VALUES ('255.5'); +SELECT * FROM t1; +DROP TABLE t1; + + +CREATE TABLE t1 (sint16 smallint not null); +INSERT INTO t1 VALUES ('0.1'); +INSERT INTO t1 VALUES ('0.5'); +INSERT INTO t1 VALUES ('32767.4'); +INSERT INTO t1 VALUES ('32767.5'); +INSERT INTO t1 VALUES ('-0.1'); +INSERT INTO t1 VALUES ('-0.5'); +INSERT INTO t1 VALUES ('-32767.4'); +INSERT INTO t1 VALUES ('-32767.5'); +INSERT INTO t1 VALUES ('-32768.4'); +INSERT INTO t1 VALUES ('-32768.5'); +SELECT * FROM t1; +DROP TABLE t1; + + +CREATE TABLE t1 (uint16 smallint unsigned not null); +INSERT INTO t1 VALUES ('0.1'); +INSERT INTO t1 VALUES ('0.5'); +INSERT INTO t1 VALUES ('32767.4'); +INSERT INTO t1 VALUES ('32767.5'); +INSERT INTO t1 VALUES ('-0.1'); +INSERT INTO t1 VALUES ('-0.5'); +INSERT INTO t1 VALUES ('65535.4'); +INSERT INTO t1 VALUES ('65535.5'); +SELECT * FROM t1; +DROP TABLE t1; + +CREATE TABLE t1 (sint24 mediumint not null); +INSERT INTO t1 VALUES ('0.1'); +INSERT INTO t1 VALUES ('0.5'); +INSERT INTO t1 VALUES ('8388607.4'); +INSERT INTO t1 VALUES ('8388607.5'); +INSERT INTO t1 VALUES ('-0.1'); +INSERT INTO t1 VALUES ('-0.5'); +INSERT INTO t1 VALUES ('-8388607.4'); +INSERT INTO t1 VALUES ('-8388607.5'); +INSERT INTO t1 VALUES ('-8388608.4'); +INSERT INTO t1 VALUES ('-8388608.5'); +SELECT * FROM t1; +DROP TABLE t1; + +CREATE TABLE t1 (uint24 mediumint unsigned not null); +INSERT INTO t1 VALUES ('0.1'); +INSERT INTO t1 VALUES ('0.5'); +INSERT INTO t1 VALUES ('8388607.4'); +INSERT INTO t1 VALUES ('8388607.5'); +INSERT INTO t1 VALUES ('-0.1'); +INSERT INTO t1 VALUES ('-0.5'); +INSERT INTO t1 VALUES ('16777215.4'); +INSERT INTO t1 VALUES ('16777215.5'); +SELECT * FROM t1; +DROP TABLE t1; + +CREATE TABLE t1 (sint64 bigint not null); +INSERT INTO t1 VALUES ('0.1'); +INSERT INTO t1 VALUES ('0.5'); +INSERT INTO t1 VALUES ('9223372036854775807.4'); +INSERT INTO t1 VALUES ('9223372036854775807.5'); +INSERT INTO t1 VALUES ('-0.1'); +INSERT INTO t1 VALUES ('-0.5'); +INSERT INTO t1 VALUES ('-9223372036854775807.4'); +INSERT INTO t1 VALUES ('-9223372036854775807.5'); +INSERT INTO t1 VALUES ('-9223372036854775808.4'); +INSERT INTO t1 VALUES ('-9223372036854775808.5'); +SELECT * FROM t1; +DROP TABLE t1; + +CREATE TABLE t1 (uint64 bigint unsigned not null); +INSERT INTO t1 VALUES ('0.1'); +INSERT INTO t1 VALUES ('0.5'); +INSERT INTO t1 VALUES ('9223372036854775807.4'); +INSERT INTO t1 VALUES ('9223372036854775807.5'); +INSERT INTO t1 VALUES ('-0.1'); +INSERT INTO t1 VALUES ('-0.5'); +INSERT INTO t1 VALUES ('18446744073709551615.4'); +INSERT INTO t1 VALUES ('18446744073709551615.5'); +INSERT INTO t1 VALUES ('1844674407370955161.0'); +INSERT INTO t1 VALUES ('1844674407370955161.1'); +INSERT INTO t1 VALUES ('1844674407370955161.2'); +INSERT INTO t1 VALUES ('1844674407370955161.3'); +INSERT INTO t1 VALUES ('1844674407370955161.4'); +INSERT INTO t1 VALUES ('1844674407370955161.5'); +INSERT INTO t1 VALUES ('1844674407370955161.0e1'); +INSERT INTO t1 VALUES ('1844674407370955161.1e1'); +INSERT INTO t1 VALUES ('1844674407370955161.2e1'); +INSERT INTO t1 VALUES ('1844674407370955161.3e1'); +INSERT INTO t1 VALUES ('1844674407370955161.4e1'); +INSERT INTO t1 VALUES ('1844674407370955161.5e1'); +INSERT INTO t1 VALUES ('18446744073709551610e-1'); +INSERT INTO t1 VALUES ('18446744073709551611e-1'); +INSERT INTO t1 VALUES ('18446744073709551612e-1'); +INSERT INTO t1 VALUES ('18446744073709551613e-1'); +INSERT INTO t1 VALUES ('18446744073709551614e-1'); +INSERT INTO t1 VALUES ('18446744073709551615e-1'); +SELECT * FROM t1; +DROP TABLE t1; + +CREATE TABLE t1 (str varchar(128), sint64 bigint not null default 0); +INSERT INTO t1 (str) VALUES ('1.5'); +INSERT INTO t1 (str) VALUES ('1.00005e4'); +INSERT INTO t1 (str) VALUES ('1.0005e3'); +INSERT INTO t1 (str) VALUES ('1.005e2'); +INSERT INTO t1 (str) VALUES ('1.05e1'); +INSERT INTO t1 (str) VALUES ('1.5e0'); +INSERT INTO t1 (str) VALUES ('100005e-1'); +INSERT INTO t1 (str) VALUES ('100050e-2'); +INSERT INTO t1 (str) VALUES ('100500e-3'); +INSERT INTO t1 (str) VALUES ('105000e-4'); +INSERT INTO t1 (str) VALUES ('150000e-5'); +UPDATE t1 SET sint64=str; +SELECT * FROM t1; +DROP TABLE t1; + + diff --git a/mysql-test/t/strict.test b/mysql-test/t/strict.test index 6f22b81172d..6ebbb53ed8e 100644 --- a/mysql-test/t/strict.test +++ b/mysql-test/t/strict.test @@ -649,9 +649,9 @@ UPDATE t1 SET col2 =col2 + 50 WHERE col2 > 0; UPDATE t1 SET col1 =col1 / 0 WHERE col1 > 0; --error 1365 UPDATE t1 SET col1= MOD(col1,0) WHERE col1 > 0; ---error 1264 +--error 1366 INSERT INTO t1 (col1) VALUES (''); ---error 1264 +--error 1366 INSERT INTO t1 (col1) VALUES ('a59b'); --error 1265 INSERT INTO t1 (col1) VALUES ('1a'); @@ -710,9 +710,9 @@ INSERT INTO t1 (col2) VALUES(18446744073709551616.0); UPDATE t1 SET col1 =col1 / 0 WHERE col1 > 0; --error 1365 UPDATE t1 SET col1= MOD(col1,0) WHERE col1 > 0; ---error 1264 +--error 1366 INSERT INTO t1 (col1) VALUES (''); ---error 1264 +--error 1366 INSERT INTO t1 (col1) VALUES ('a59b'); --error 1265 INSERT INTO t1 (col1) VALUES ('1a'); diff --git a/mysql-test/t/type_bit.test b/mysql-test/t/type_bit.test index 998f8f18fbe..d46ba667665 100644 --- a/mysql-test/t/type_bit.test +++ b/mysql-test/t/type_bit.test @@ -252,5 +252,13 @@ select hex(b + 0), bin(b + 0), oct(b + 0), hex(n), bin(n), oct(n) from bug15583; select conv(b, 10, 2), conv(b + 0, 10, 2) from bug15583; drop table bug15583; +# +# Bug #22271: data casting may affect data stored in the next column(s?) +# + +create table t1(a bit(1), b smallint unsigned); +insert into t1 (b, a) values ('2', '1'); +select hex(a), b from t1; +drop table t1; --echo End of 5.0 tests diff --git a/mysql-test/t/type_float.test b/mysql-test/t/type_float.test index 5bfd744e4a8..965826629bd 100644 --- a/mysql-test/t/type_float.test +++ b/mysql-test/t/type_float.test @@ -178,7 +178,16 @@ show warnings; desc t3; drop table t1,t2,t3; -# End of 4.1 tests +# +# Bug #22129: A small double precision number becomes zero +# +# check if underflows are detected correctly +select 1e-308, 1.00000001e-300, 100000000e-300; + +# check if overflows are detected correctly +select 10e307; + +--echo End of 4.1 tests # # bug #12694 (float(m,d) specifications) diff --git a/mysql-test/t/warnings.test b/mysql-test/t/warnings.test index 4768c7574e5..5e9d25aa09b 100644 --- a/mysql-test/t/warnings.test +++ b/mysql-test/t/warnings.test @@ -156,4 +156,60 @@ select * from t1 limit 1, 0; select * from t1 limit 0, 0; drop table t1; -# End of 4.1 tests +--echo End of 4.1 tests + +# +# Bug#20778: strange characters in warning message 1366 when called in SP +# + +let $engine_type= innodb; + +CREATE TABLE t1( f1 CHAR(20) ); +CREATE TABLE t2( f1 CHAR(20), f2 CHAR(25) ); +CREATE TABLE t3( f1 CHAR(20), f2 CHAR(25), f3 DATE ); + +INSERT INTO t1 VALUES ( 'a`' ); +INSERT INTO t2 VALUES ( 'a`', 'a`' ); +INSERT INTO t3 VALUES ( 'a`', 'a`', '1000-01-1' ); + +DROP PROCEDURE IF EXISTS sp1; +DROP PROCEDURE IF EXISTS sp2; +DROP PROCEDURE IF EXISTS sp3; +delimiter //; +CREATE PROCEDURE sp1() +BEGIN + DECLARE x NUMERIC ZEROFILL; + SELECT f1 INTO x FROM t1 LIMIT 1; +END// +CREATE PROCEDURE sp2() +BEGIN + DECLARE x NUMERIC ZEROFILL; + SELECT f1 INTO x FROM t2 LIMIT 1; +END// +CREATE PROCEDURE sp3() +BEGIN + DECLARE x NUMERIC ZEROFILL; + SELECT f1 INTO x FROM t3 LIMIT 1; +END// +delimiter ;// +CALL sp1(); +CALL sp2(); +CALL sp3(); + +DROP PROCEDURE IF EXISTS sp1; +delimiter //; +CREATE PROCEDURE sp1() +BEGIN +declare x numeric unsigned zerofill; +SELECT f1 into x from t2 limit 1; +END// +delimiter ;// +CALL sp1(); +DROP TABLE t1; +DROP TABLE t2; +DROP TABLE t3; +DROP PROCEDURE sp1; +DROP PROCEDURE sp2; +DROP PROCEDURE sp3; + +--echo End of 5.0 tests diff --git a/mysql-test/valgrind.supp b/mysql-test/valgrind.supp index 24426727968..f7eb9baa4c7 100644 --- a/mysql-test/valgrind.supp +++ b/mysql-test/valgrind.supp @@ -15,6 +15,14 @@ } { + pthread allocate_tls memory loss + Memcheck:Leak + fun:calloc + fun:_dl_allocate_tls + fun:pthread_create* +} + +{ pthread allocate_dtv memory loss Memcheck:Leak fun:calloc @@ -115,6 +123,24 @@ } { + libz longest_match 3 + Memcheck:Cond + fun:longest_match + fun:deflate_slow + fun:deflate + fun:gzclose +} + +{ + libz longest_match 4 + Memcheck:Cond + fun:longest_match + fun:deflate_slow + fun:deflate + fun:gzflush +} + +{ libz deflate Memcheck:Cond obj:*/libz.so.* @@ -133,6 +159,7 @@ fun:gzflush } + # # Warning from my_thread_init becasue mysqld dies before kill thread exists # diff --git a/mysys/my_libwrap.c b/mysys/my_libwrap.c index be8adbab0a1..80fca127716 100644 --- a/mysys/my_libwrap.c +++ b/mysys/my_libwrap.c @@ -31,12 +31,12 @@ void my_fromhost(struct request_info *req) int my_hosts_access(struct request_info *req) { - hosts_access(req); + return hosts_access(req); } char *my_eval_client(struct request_info *req) { - eval_client(req); + return eval_client(req); } #endif /* HAVE_LIBWRAP */ diff --git a/netware/BUILD/mwccnlm b/netware/BUILD/mwccnlm index e6840e781f8..030d87288f2 100755 --- a/netware/BUILD/mwccnlm +++ b/netware/BUILD/mwccnlm @@ -3,9 +3,12 @@ # stop on errors set -e -# mwccnlm is having a hard time understanding "-I./../include" -# convert it to "-I../include" -args=" "`echo $* | sed -e 's/-I.\/../-I../g'` +# mwccnlm is having a hard time understanding: +# * "-I./../include", convert it to "-I../include" +# * "-I.../..", convert it to "-I../../" +args=" "`echo $* | sed \ +-e 's/-I.\/../-I../g' \ +-e 's/\(-I[.\/]*.\) /\1\/ /g'` # NOTE: Option 'pipefail' is not standard sh set -o pipefail diff --git a/netware/BUILD/mwenv b/netware/BUILD/mwenv index fa52568fcd6..d8d53293b2c 100755 --- a/netware/BUILD/mwenv +++ b/netware/BUILD/mwenv @@ -1,19 +1,39 @@ #! /bin/sh -# F:/mydev, /home/kp/mydev, and 4.0.21 must be correct before compiling -# This values are normally changed by the nwbootstrap script +if test ! -r ./sql/mysqld.cc +then + echo "you must start from the top source directory" + exit 1 +fi -# the default is "F:/mydev" -export MYDEV="F:/mydev" +# The base path(in wineformat) where compilers, includes and +# libraries are installed +if test -z $MYDEV +then + # the default is "F:/mydev" + export MYDEV="F:/mydev" +fi +echo "MYDEV: $MYDEV" -export MWCNWx86Includes="$MYDEV/libc/include;$MYDEV/fs64/headers;$MYDEV/zlib-1.1.4;$MYDEV/mysql-VERSION/include;$MYDEV" -export MWNWx86Libraries="$MYDEV/libc/imports;$MYDEV/mw/lib;$MYDEV/fs64/imports;$MYDEV/zlib-1.1.4;$MYDEV/openssl;$MYDEV/mysql-VERSION/netware/BUILD" +# Get current dir +BUILD_DIR=`pwd` +echo "BUILD_DIR: $BUILD_DIR" + +# Get current dir in wine format +base=`echo $MYDEV |sed 's/\/.*//'` +base_unix_part=`winepath -- -u $base/` +WINE_BUILD_DIR=`echo "$BUILD_DIR" | sed 's_'$base_unix_part'/__'` +WINE_BUILD_DIR="$base/$WINE_BUILD_DIR" +echo "WINE_BUILD_DIR: $WINE_BUILD_DIR" + +export MWCNWx86Includes="$MYDEV/libc/include;$MYDEV/fs64/headers;$MYDEV/zlib-1.2.3;$WINE_BUILD_DIR/include;$MYDEV" +export MWNWx86Libraries="$MYDEV/libc/imports;$MYDEV/mw/lib;$MYDEV/fs64/imports;$MYDEV/zlib-1.2.3;$MYDEV/openssl;$WINE_BUILD_DIR/netware/BUILD" export MWNWx86LibraryFiles="libcpre.o;libc.imp;netware.imp;mwcrtl.lib;mwcpp.lib;libz.a;neb.imp;zPublics.imp;knetware.imp" export WINEPATH="$MYDEV/mw/bin" -# the default added path is "$HOME/mydev/mysql-x.x-x/netware/BUILD" -export PATH="$PATH:BUILD_DIR/mysql-VERSION/netware/BUILD" +# the default added path is "$BUILD_DIR/netware/BUILD" +export PATH="$PATH:$BUILD_DIR/netware/BUILD" export AR='mwldnlm' export AR_FLAGS='-type library -o' diff --git a/netware/Makefile.am b/netware/Makefile.am index 2d34283c4b3..648ce79c484 100644 --- a/netware/Makefile.am +++ b/netware/Makefile.am @@ -23,7 +23,8 @@ mysqld_safe_SOURCES= mysqld_safe.c my_manage.c mysql_install_db_SOURCES= mysql_install_db.c my_manage.c mysql_test_run_SOURCES= mysql_test_run.c my_manage.c libmysql_SOURCES= libmysqlmain.c -libmysql_LDADD = ../libmysql/.libs/libmysqlclient.a @openssl_libs@ +libmysql_LDADD = ../libmysql/.libs/libmysqlclient.a \ + @openssl_libs@ @yassl_libs@ netware_build_files = client/mysql.def client/mysqladmin.def \ client/mysqlbinlog.def client/mysqlcheck.def \ @@ -45,8 +46,20 @@ link_sources: @LN_CP_F@ $(srcdir)/$$org ../$$f; \ done else -EXTRA_DIST= comp_err.def init_db.sql install_test_db.ncf \ - libmysql.def libmysql.imp \ + +BUILT_SOURCES = libmysql.imp +DISTCLEANFILES = $(BUILT_SOURCES) + +# Create the libmysql.imp from libmysql/libmysql.def +libmysql.imp: $(top_srcdir)/libmysql/libmysql.def + awk 'BEGIN{x=0;} \ + END{printf("\n");} \ + x==1 {printf(" %s",$$1); x++; next} \ + x>1 {printf(",\n %s", $$1); next} \ + /EXPORTS/{x=1}' $(top_srcdir)/libmysql/libmysql.def > libmysql.imp + +EXTRA_DIST= $(BUILT_SOURCES) comp_err.def init_db.sql install_test_db.ncf \ + libmysql.def \ libmysqlmain.c my_manage.c my_manage.h \ my_print_defaults.def myisam_ftdump.def myisamchk.def \ myisamlog.def myisampack.def mysql.def mysql.xdc \ diff --git a/netware/libmysql.imp b/netware/libmysql.imp deleted file mode 100644 index 977fb1b0b1f..00000000000 --- a/netware/libmysql.imp +++ /dev/null @@ -1,85 +0,0 @@ -myodbc_remove_escape,
-mysql_add_slave,
-mysql_affected_rows,
-mysql_change_user,
-mysql_character_set_name,
-mysql_close,
-mysql_data_seek,
-mysql_debug,
-mysql_disable_reads_from_master,
-mysql_disable_rpl_parse,
-mysql_dump_debug_info,
-mysql_enable_reads_from_master,
-mysql_enable_rpl_parse,
-mysql_eof,
-mysql_errno,
-mysql_error,
-mysql_escape_string,
-mysql_fetch_field,
-mysql_fetch_field_direct,
-mysql_fetch_fields,
-mysql_fetch_lengths,
-mysql_fetch_row,
-mysql_field_count,
-mysql_field_seek,
-mysql_field_tell,
-mysql_free_result,
-mysql_get_client_info,
-mysql_get_host_info,
-mysql_get_proto_info,
-mysql_get_server_info,
-mysql_info,
-mysql_init,
-mysql_insert_id,
-mysql_kill,
-mysql_list_dbs,
-mysql_list_fields,
-mysql_list_processes,
-mysql_list_tables,
-mysql_manager_close,
-mysql_manager_command,
-mysql_manager_connect,
-mysql_manager_fetch_line,
-mysql_manager_init,
-mysql_master_query,
-mysql_master_send_query,
-mysql_num_fields,
-mysql_num_rows,
-mysql_odbc_escape_string,
-mysql_options,
-mysql_ping,
-mysql_query,
-mysql_read_query_result,
-mysql_reads_from_master_enabled,
-mysql_real_connect,
-mysql_real_escape_string,
-mysql_real_query,
-mysql_refresh,
-mysql_row_seek,
-mysql_row_tell,
-mysql_rpl_parse_enabled,
-mysql_rpl_probe,
-mysql_rpl_query_type,
-mysql_select_db,
-mysql_send_query,
-mysql_server_end,
-mysql_server_init,
-mysql_set_master,
-mysql_shutdown,
-mysql_slave_query,
-mysql_slave_send_query,
-mysql_ssl_set,
-mysql_stat,
-mysql_store_result,
-mysql_thread_end,
-mysql_thread_id,
-mysql_thread_init,
-mysql_thread_safe,
-mysql_use_result,
-net_safe_read,
-#simple_command, -mysql_connect,
-mysql_create_db,
-mysql_drop_db,
-
-
diff --git a/scripts/mysqlhotcopy.sh b/scripts/mysqlhotcopy.sh index bf53aa78e15..61cd59457d1 100644 --- a/scripts/mysqlhotcopy.sh +++ b/scripts/mysqlhotcopy.sh @@ -263,6 +263,7 @@ my $hc_locks = ""; my $hc_tables = ""; my $num_tables = 0; my $num_files = 0; +my $raid_dir_regex = '[A-Za-z0-9]{2}'; foreach my $rdb ( @db_desc ) { my $db = $rdb->{src}; @@ -294,7 +295,7 @@ foreach my $rdb ( @db_desc ) { my @raid_dir = (); while ( defined( my $name = readdir DBDIR ) ) { - if ( $name =~ /^\d\d$/ && -d "$db_dir/$name" ) { + if ( $name =~ /^$raid_dir_regex$/ && -d "$db_dir/$name" ) { push @raid_dir, $name; } else { @@ -602,7 +603,7 @@ sub copy_files { # add recursive option for scp $cp.= " -r" if $^O =~ /m^(solaris|linux|freebsd|darwin)$/ && $method =~ /^scp\b/; - my @non_raid = map { "'$_'" } grep { ! m:/\d{2}/[^/]+$: } @$files; + my @non_raid = map { "'$_'" } grep { ! m:/$raid_dir_regex/[^/]+$: } @$files; # add files to copy and the destination directory safe_system( $cp, @non_raid, "'$target'" ) if (@non_raid); @@ -810,7 +811,7 @@ sub get_raid_dirs { my %dirs = (); foreach my $f ( @$r_files ) { - if ( $f =~ m:^(\d\d)/: ) { + if ( $f =~ m:^($raid_dir_regex)/: ) { $dirs{$1} = 1; } } diff --git a/sql/Makefile.am b/sql/Makefile.am index e837e10472c..d9cea960915 100644 --- a/sql/Makefile.am +++ b/sql/Makefile.am @@ -27,7 +27,7 @@ INCLUDES = @ZLIB_INCLUDES@ \ WRAPLIBS= @WRAPLIBS@ SUBDIRS = share libexec_PROGRAMS = mysqld -noinst_PROGRAMS = gen_lex_hash +EXTRA_PROGRAMS = gen_lex_hash bin_PROGRAMS = mysql_tzinfo_to_sql gen_lex_hash_LDFLAGS = @NOINST_LDFLAGS@ LDADD = $(top_builddir)/myisam/libmyisam.a \ @@ -153,7 +153,11 @@ sql_yacc.o: sql_yacc.cc sql_yacc.h $(HEADERS) @echo "If it fails, re-run configure with --with-low-memory" $(CXXCOMPILE) $(LM_CFLAGS) -c $< -lex_hash.h: gen_lex_hash$(EXEEXT) +# This generates lex_hash.h +# NOTE Built sources should depend on their sources not the tool +# this avoid the rebuild of the built files in a source dist +lex_hash.h: gen_lex_hash.cc lex.h + $(MAKE) $(AM_MAKEFLAGS) gen_lex_hash$(EXEEXT) ./gen_lex_hash$(EXEEXT) > $@ # For testing of udf_example.so diff --git a/sql/field.cc b/sql/field.cc index 4860f6ea3da..9b512fc6d4b 100644 --- a/sql/field.cc +++ b/sql/field.cc @@ -2316,11 +2316,16 @@ int Field_new_decimal::store(const char *from, uint length, from, length, charset, &decimal_value)) && table->in_use->abort_on_warning) { + /* Because "from" is not NUL-terminated and we use %s in the ER() */ + String from_as_str; + from_as_str.copy(from, length, &my_charset_bin); + push_warning_printf(table->in_use, MYSQL_ERROR::WARN_LEVEL_ERROR, ER_TRUNCATED_WRONG_VALUE_FOR_FIELD, ER(ER_TRUNCATED_WRONG_VALUE_FOR_FIELD), - "decimal", from, field_name, + "decimal", from_as_str.c_ptr(), field_name, (ulong) table->in_use->row_count); + DBUG_RETURN(err); } @@ -2333,13 +2338,20 @@ int Field_new_decimal::store(const char *from, uint length, set_value_on_overflow(&decimal_value, decimal_value.sign()); break; case E_DEC_BAD_NUM: + { + /* Because "from" is not NUL-terminated and we use %s in the ER() */ + String from_as_str; + from_as_str.copy(from, length, &my_charset_bin); + push_warning_printf(table->in_use, MYSQL_ERROR::WARN_LEVEL_WARN, ER_TRUNCATED_WRONG_VALUE_FOR_FIELD, ER(ER_TRUNCATED_WRONG_VALUE_FOR_FIELD), - "decimal", from, field_name, + "decimal", from_as_str.c_ptr(), field_name, (ulong) table->in_use->row_count); my_decimal_set_zero(&decimal_value); + break; + } } #ifndef DBUG_OFF @@ -2482,30 +2494,27 @@ void Field_new_decimal::sql_type(String &str) const int Field_tiny::store(const char *from,uint len,CHARSET_INFO *cs) { - int not_used; // We can ignore result from str2int char *end; - long tmp= my_strntol(cs, from, len, 10, &end, ¬_used); - int error= 0; + int error; if (unsigned_flag) { - if (tmp < 0) - { - tmp=0; /* purecov: inspected */ - set_warning(MYSQL_ERROR::WARN_LEVEL_WARN, ER_WARN_DATA_OUT_OF_RANGE, 1); - error= 1; - } - else if (tmp > 255) + ulonglong tmp= cs->cset->strntoull10rnd(cs, from, len, 1, &end, &error); + if (error == MY_ERRNO_ERANGE || tmp > 255) { - tmp= 255; + set_if_smaller(tmp, 255); set_warning(MYSQL_ERROR::WARN_LEVEL_WARN, ER_WARN_DATA_OUT_OF_RANGE, 1); error= 1; } else if (table->in_use->count_cuted_fields && check_int(from,len,end,cs)) error= 1; + else + error= 0; + ptr[0]= (char) tmp; } else { + longlong tmp= cs->cset->strntoull10rnd(cs, from, len, 0, &end, &error); if (tmp < -128) { tmp= -128; @@ -2520,8 +2529,10 @@ int Field_tiny::store(const char *from,uint len,CHARSET_INFO *cs) } else if (table->in_use->count_cuted_fields && check_int(from,len,end,cs)) error= 1; + else + error= 0; + ptr[0]= (char) tmp; } - ptr[0]= (char) tmp; return error; } @@ -2686,30 +2697,34 @@ void Field_tiny::sql_type(String &res) const int Field_short::store(const char *from,uint len,CHARSET_INFO *cs) { - int not_used; // We can ignore result from str2int char *end; - long tmp= my_strntol(cs, from, len, 10, &end, ¬_used); - int error= 0; + int error; if (unsigned_flag) { - if (tmp < 0) + ulonglong tmp= cs->cset->strntoull10rnd(cs, from, len, 1, &end, &error); + if (error == MY_ERRNO_ERANGE || tmp > UINT_MAX16) { - tmp=0; - set_warning(MYSQL_ERROR::WARN_LEVEL_WARN, ER_WARN_DATA_OUT_OF_RANGE, 1); - error= 1; - } - else if (tmp > UINT_MAX16) - { - tmp=UINT_MAX16; + set_if_smaller(tmp, UINT_MAX16); set_warning(MYSQL_ERROR::WARN_LEVEL_WARN, ER_WARN_DATA_OUT_OF_RANGE, 1); error= 1; } else if (table->in_use->count_cuted_fields && check_int(from,len,end,cs)) error= 1; + else + error= 0; +#ifdef WORDS_BIGENDIAN + if (table->s->db_low_byte_first) + { + int2store(ptr,tmp); + } + else +#endif + shortstore(ptr,(short) tmp); } else { + longlong tmp= cs->cset->strntoull10rnd(cs, from, len, 0, &end, &error); if (tmp < INT_MIN16) { tmp= INT_MIN16; @@ -2724,15 +2739,17 @@ int Field_short::store(const char *from,uint len,CHARSET_INFO *cs) } else if (table->in_use->count_cuted_fields && check_int(from,len,end,cs)) error= 1; - } + else + error= 0; #ifdef WORDS_BIGENDIAN - if (table->s->db_low_byte_first) - { - int2store(ptr,tmp); - } - else + if (table->s->db_low_byte_first) + { + int2store(ptr,tmp); + } + else #endif - shortstore(ptr,(short) tmp); + shortstore(ptr,(short) tmp); + } return error; } @@ -2960,30 +2977,27 @@ void Field_short::sql_type(String &res) const int Field_medium::store(const char *from,uint len,CHARSET_INFO *cs) { - int not_used; // We can ignore result from str2int char *end; - long tmp= my_strntol(cs, from, len, 10, &end, ¬_used); - int error= 0; + int error; if (unsigned_flag) { - if (tmp < 0) - { - tmp=0; - set_warning(MYSQL_ERROR::WARN_LEVEL_WARN, ER_WARN_DATA_OUT_OF_RANGE, 1); - error= 1; - } - else if (tmp >= (long) (1L << 24)) + ulonglong tmp= cs->cset->strntoull10rnd(cs, from, len, 1, &end, &error); + if (error == MY_ERRNO_ERANGE || tmp > UINT_MAX24) { - tmp=(long) (1L << 24)-1L; + set_if_smaller(tmp, UINT_MAX24); set_warning(MYSQL_ERROR::WARN_LEVEL_WARN, ER_WARN_DATA_OUT_OF_RANGE, 1); error= 1; } else if (table->in_use->count_cuted_fields && check_int(from,len,end,cs)) error= 1; + else + error= 0; + int3store(ptr,tmp); } else { + longlong tmp= cs->cset->strntoull10rnd(cs, from, len, 0, &end, &error); if (tmp < INT_MIN24) { tmp= INT_MIN24; @@ -2998,9 +3012,10 @@ int Field_medium::store(const char *from,uint len,CHARSET_INFO *cs) } else if (table->in_use->count_cuted_fields && check_int(from,len,end,cs)) error= 1; + else + error= 0; + int3store(ptr,tmp); } - - int3store(ptr,tmp); return error; } @@ -3196,64 +3211,47 @@ static bool test_if_minus(CHARSET_INFO *cs, int Field_long::store(const char *from,uint len,CHARSET_INFO *cs) { - ulong tmp_scan; - longlong tmp; long store_tmp; int error; char *end; - tmp_scan= cs->cset->scan(cs, from, from+len, MY_SEQ_SPACES); - len-= tmp_scan; - from+= tmp_scan; - - end= (char*) from+len; - tmp= cs->cset->strtoll10(cs, from, &end, &error); - - if (error != MY_ERRNO_EDOM) + if (unsigned_flag) { - if (unsigned_flag) + ulonglong tmp= cs->cset->strntoull10rnd(cs, from, len, 1, &end, &error); + if (error == MY_ERRNO_ERANGE || tmp > (ulonglong) UINT_MAX32) { - if (error < 0) - { - error= 1; - tmp= 0; - } - else if ((ulonglong) tmp > (ulonglong) UINT_MAX32) - { - tmp= UINT_MAX32; - error= 1; - } - else - error= 0; + set_if_smaller(tmp, (ulonglong) UINT_MAX32); + set_warning(MYSQL_ERROR::WARN_LEVEL_WARN, ER_WARN_DATA_OUT_OF_RANGE, 1); + error= 1; } + else if (table->in_use->count_cuted_fields && check_int(from,len,end,cs)) + error= 1; else - { - if (error < 0) - { - error= 0; - if (tmp < INT_MIN32) - { - tmp= INT_MIN32; - error= 1; - } - } - else if (tmp > INT_MAX32) - { - tmp= INT_MAX32; - error= 1; - } - } + error= 0; + store_tmp= (long) tmp; } - if (error) + else { - error= error != MY_ERRNO_EDOM ? 1 : 2; - set_warning(MYSQL_ERROR::WARN_LEVEL_WARN, ER_WARN_DATA_OUT_OF_RANGE, 1); + longlong tmp= cs->cset->strntoull10rnd(cs, from, len, 0, &end, &error); + if (tmp < INT_MIN32) + { + tmp= INT_MIN32; + set_warning(MYSQL_ERROR::WARN_LEVEL_WARN, ER_WARN_DATA_OUT_OF_RANGE, 1); + error= 1; + } + else if (tmp > INT_MAX32) + { + tmp=INT_MAX32; + set_warning(MYSQL_ERROR::WARN_LEVEL_WARN, ER_WARN_DATA_OUT_OF_RANGE, 1); + error= 1; + } + else if (table->in_use->count_cuted_fields && check_int(from,len,end,cs)) + error= 1; + else + error= 0; + store_tmp= (long) tmp; } - else if (from+len != end && table->in_use->count_cuted_fields && - check_int(from,len,end,cs)) - error= 2; - store_tmp= (long) tmp; #ifdef WORDS_BIGENDIAN if (table->s->db_low_byte_first) { @@ -3489,33 +3487,20 @@ void Field_long::sql_type(String &res) const int Field_longlong::store(const char *from,uint len,CHARSET_INFO *cs) { - longlong tmp; - int error= 0; + int error; char *end; + ulonglong tmp; - tmp= cs->cset->scan(cs, from, from+len, MY_SEQ_SPACES); - len-= (uint)tmp; - from+= tmp; - if (unsigned_flag) - { - if (!len || test_if_minus(cs, from, from + len)) - { - tmp=0; // Set negative to 0 - error= 1; - } - else - tmp=(longlong) my_strntoull(cs,from,len,10,&end,&error); - } - else - tmp=my_strntoll(cs,from,len,10,&end,&error); - if (error) + tmp= cs->cset->strntoull10rnd(cs,from,len,unsigned_flag,&end,&error); + if (error == MY_ERRNO_ERANGE) { set_warning(MYSQL_ERROR::WARN_LEVEL_WARN, ER_WARN_DATA_OUT_OF_RANGE, 1); error= 1; } - else if (from+len != end && table->in_use->count_cuted_fields && - check_int(from,len,end,cs)) - error= 2; + else if (table->in_use->count_cuted_fields && check_int(from,len,end,cs)) + error= 1; + else + error= 0; #ifdef WORDS_BIGENDIAN if (table->s->db_low_byte_first) { @@ -7921,7 +7906,7 @@ int Field_bit::store(const char *from, uint length, CHARSET_INFO *cs) (delta == -1 && (uchar) *from > ((1 << bit_len) - 1)) || (!bit_len && delta < 0)) { - set_rec_bits(0xff, bit_ptr, bit_ofs, bit_len); + set_rec_bits((1 << bit_len) - 1, bit_ptr, bit_ofs, bit_len); memset(ptr, 0xff, bytes_in_rec); if (table->in_use->really_abort_on_warning()) set_warning(MYSQL_ERROR::WARN_LEVEL_ERROR, ER_DATA_TOO_LONG, 1); @@ -8877,7 +8862,7 @@ create_field::create_field(Field *old_field,Field *orig_field) case 3: sql_type= FIELD_TYPE_MEDIUM_BLOB; break; default: sql_type= FIELD_TYPE_LONG_BLOB; break; } - length=(length+charset->mbmaxlen-1) / charset->mbmaxlen; + length/= charset->mbmaxlen; key_length/= charset->mbmaxlen; break; case MYSQL_TYPE_STRING: diff --git a/sql/field_conv.cc b/sql/field_conv.cc index 3200f2ca9b2..95ff985376d 100644 --- a/sql/field_conv.cc +++ b/sql/field_conv.cc @@ -428,6 +428,21 @@ static void do_varstring2(Copy_field *copy) length); } + +static void do_varstring2_mb(Copy_field *copy) +{ + int well_formed_error; + CHARSET_INFO *cs= copy->from_field->charset(); + uint char_length= (copy->to_length - HA_KEY_BLOB_LENGTH) / cs->mbmaxlen; + uint from_length= uint2korr(copy->from_ptr); + const char *from_beg= copy->from_ptr + HA_KEY_BLOB_LENGTH; + uint length= cs->cset->well_formed_len(cs, from_beg, from_beg + from_length, + char_length, &well_formed_error); + int2store(copy->to_ptr, length); + memcpy(copy->to_ptr+HA_KEY_BLOB_LENGTH, from_beg, length); +} + + /*************************************************************************** ** The different functions that fills in a Copy_field class ***************************************************************************/ @@ -587,7 +602,8 @@ void (*Copy_field::get_copy_func(Field *to,Field *from))(Copy_field*) return do_field_string; if (to_length != from_length) return (((Field_varstring*) to)->length_bytes == 1 ? - do_varstring1 : do_varstring2); + do_varstring1 : (from->charset()->mbmaxlen == 1 ? + do_varstring2 : do_varstring2_mb)); } else if (to_length < from_length) return (from->charset()->mbmaxlen == 1 ? diff --git a/sql/ha_innodb.cc b/sql/ha_innodb.cc index 4e73d4fb285..e99d93784c9 100644 --- a/sql/ha_innodb.cc +++ b/sql/ha_innodb.cc @@ -5970,19 +5970,6 @@ ha_innobase::start_stmt( prebuilt->select_lock_type = prebuilt->stored_select_lock_type; } - - if (prebuilt->stored_select_lock_type != LOCK_S - && prebuilt->stored_select_lock_type != LOCK_X) { - sql_print_error("stored_select_lock_type is %lu inside " - "::start_stmt()!", - prebuilt->stored_select_lock_type); - - /* Set the value to LOCK_X: this is just fault - tolerance, we do not know what the correct value - should be! */ - - prebuilt->select_lock_type = LOCK_X; - } } trx->detailed_error[0] = '\0'; diff --git a/sql/item_strfunc.cc b/sql/item_strfunc.cc index 46a96c28d88..31c2f44fc3e 100644 --- a/sql/item_strfunc.cc +++ b/sql/item_strfunc.cc @@ -1149,12 +1149,13 @@ void Item_func_substr::fix_length_and_dec() } if (arg_count == 3 && args[2]->const_item()) { - int32 length= (int32) args[2]->val_int() * collation.collation->mbmaxlen; + int32 length= (int32) args[2]->val_int(); if (length <= 0) max_length=0; /* purecov: inspected */ else set_if_smaller(max_length,(uint) length); } + max_length*= collation.collation->mbmaxlen; } diff --git a/sql/item_timefunc.cc b/sql/item_timefunc.cc index 30230005f6e..48d6458bd88 100644 --- a/sql/item_timefunc.cc +++ b/sql/item_timefunc.cc @@ -65,7 +65,7 @@ static bool make_datetime(date_time_format_types format, TIME *ltime, ltime->hour, ltime->minute, ltime->second); break; case TIME_MICROSECOND: - length= cs->cset->snprintf(cs, buff, length, "%s%02d:%02d:%02d.%06d", + length= cs->cset->snprintf(cs, buff, length, "%s%02d:%02d:%02d.%06ld", ltime->neg ? "-" : "", ltime->hour, ltime->minute, ltime->second, ltime->second_part); @@ -82,7 +82,7 @@ static bool make_datetime(date_time_format_types format, TIME *ltime, break; case DATE_TIME_MICROSECOND: length= cs->cset->snprintf(cs, buff, length, - "%04d-%02d-%02d %02d:%02d:%02d.%06d", + "%04d-%02d-%02d %02d:%02d:%02d.%06ld", ltime->year, ltime->month, ltime->day, ltime->hour, ltime->minute, ltime->second, ltime->second_part); diff --git a/sql/log.cc b/sql/log.cc index 1cd01865f9f..212c6403666 100644 --- a/sql/log.cc +++ b/sql/log.cc @@ -566,15 +566,18 @@ bool MYSQL_LOG::open(const char *log_name, case LOG_NORMAL: { char *end; - int len=my_snprintf(buff, sizeof(buff), "%s, Version: %s. " + int len=my_snprintf(buff, sizeof(buff), "%s, Version: %s (%s). " #ifdef EMBEDDED_LIBRARY - "embedded library\n", my_progname, server_version + "embedded library\n", + my_progname, server_version, MYSQL_COMPILATION_COMMENT #elif __NT__ "started with:\nTCP Port: %d, Named Pipe: %s\n", - my_progname, server_version, mysqld_port, mysqld_unix_port + my_progname, server_version, MYSQL_COMPILATION_COMMENT, + mysqld_port, mysqld_unix_port #else "started with:\nTcp port: %d Unix socket: %s\n", - my_progname,server_version,mysqld_port,mysqld_unix_port + my_progname, server_version, MYSQL_COMPILATION_COMMENT, + mysqld_port, mysqld_unix_port #endif ); end=strnmov(buff+len,"Time Id Command Argument\n", diff --git a/sql/mysql_priv.h b/sql/mysql_priv.h index c6cc6519d78..381f2a989b5 100644 --- a/sql/mysql_priv.h +++ b/sql/mysql_priv.h @@ -131,7 +131,18 @@ MY_LOCALE *my_locale_by_name(const char *name); #define MAX_ACCEPT_RETRY 10 // Test accept this many times #define MAX_FIELDS_BEFORE_HASH 32 #define USER_VARS_HASH_SIZE 16 -#define STACK_MIN_SIZE 8192 // Abort if less stack during eval. + +/* + Value of 9236 discovered through binary search 2006-09-26 on Ubuntu Dapper + Drake, libc6 2.3.6-0ubuntu2, Linux kernel 2.6.15-27-686, on x86. (Added + 100 bytes as reasonable buffer against growth and other environments' + requirements.) + + Feel free to raise this by the smallest amount you can to get the + "execution_constants" test to pass. + */ +#define STACK_MIN_SIZE 9336 // Abort if less stack during eval. + #define STACK_MIN_SIZE_FOR_OPEN 1024*80 #define STACK_BUFF_ALLOC 256 // For stack overrun checks #ifndef MYSQLD_NET_RETRY_COUNT @@ -1121,10 +1132,10 @@ bool init_errmessage(void); void sql_perror(const char *message); void vprint_msg_to_log(enum loglevel level, const char *format, va_list args); -void sql_print_error(const char *format, ...); -void sql_print_warning(const char *format, ...); -void sql_print_information(const char *format, ...); - +void sql_print_error(const char *format, ...) ATTRIBUTE_FORMAT(printf, 1, 2); +void sql_print_warning(const char *format, ...) ATTRIBUTE_FORMAT(printf, 1, 2); +void sql_print_information(const char *format, ...) + ATTRIBUTE_FORMAT(printf, 1, 2); bool fn_format_relative_to_data_home(my_string to, const char *name, diff --git a/sql/mysqld.cc b/sql/mysqld.cc index 8a4f212340d..1dd15398cd1 100644 --- a/sql/mysqld.cc +++ b/sql/mysqld.cc @@ -1025,8 +1025,8 @@ extern "C" sig_handler print_signal_warning(int sig) if (!DBUG_IN_USE) { if (global_system_variables.log_warnings) - sql_print_warning("Got signal %d from thread %d", - sig,my_thread_id()); + sql_print_warning("Got signal %d from thread %ld", + sig, my_thread_id()); } #ifdef DONT_REMEMBER_SIGNAL my_sigset(sig,print_signal_warning); /* int. thread system calls */ @@ -1531,8 +1531,8 @@ static void network_init(void) if (strlen(mysqld_unix_port) > (sizeof(UNIXaddr.sun_path) - 1)) { - sql_print_error("The socket file path is too long (> %d): %s", - sizeof(UNIXaddr.sun_path) - 1, mysqld_unix_port); + sql_print_error("The socket file path is too long (> %lu): %s", + sizeof(UNIXaddr.sun_path) - 1, mysqld_unix_port); unireg_abort(1); } if ((unix_sock= socket(AF_UNIX, SOCK_STREAM, 0)) < 0) @@ -2912,7 +2912,7 @@ static void openssl_lock(int mode, openssl_lock_t *lock, const char *file, } if (err) { - sql_print_error("Fatal: can't %s OpenSSL %s lock", what); + sql_print_error("Fatal: can't %s OpenSSL lock", what); abort(); } } @@ -7042,14 +7042,15 @@ get_one_option(int optid, const struct my_option *opt __attribute__((unused)), exit(1); } switch (method-1) { - case 0: - method_conv= MI_STATS_METHOD_NULLS_NOT_EQUAL; + case 2: + method_conv= MI_STATS_METHOD_IGNORE_NULLS; break; case 1: method_conv= MI_STATS_METHOD_NULLS_EQUAL; break; - case 2: - method_conv= MI_STATS_METHOD_IGNORE_NULLS; + case 0: + default: + method_conv= MI_STATS_METHOD_NULLS_NOT_EQUAL; break; } global_system_variables.myisam_stats_method= method_conv; diff --git a/sql/opt_range.cc b/sql/opt_range.cc index 959d7b7e381..737a296e1d7 100644 --- a/sql/opt_range.cc +++ b/sql/opt_range.cc @@ -5559,8 +5559,9 @@ void SEL_ARG::test_use_count(SEL_ARG *root) ulong count=count_key_part_usage(root,pos->next_key_part); if (count > pos->next_key_part->use_count) { - sql_print_information("Use_count: Wrong count for key at 0x%lx, %lu should be %lu", - pos,pos->next_key_part->use_count,count); + sql_print_information("Use_count: Wrong count for key at 0x%lx, %lu " + "should be %lu", (long unsigned int)pos, + pos->next_key_part->use_count, count); return; } pos->next_key_part->test_use_count(root); @@ -5568,7 +5569,7 @@ void SEL_ARG::test_use_count(SEL_ARG *root) } if (e_count != elements) sql_print_warning("Wrong use count: %u (should be %u) for tree at 0x%lx", - e_count, elements, (gptr) this); + e_count, elements, (long unsigned int) this); } #endif diff --git a/sql/set_var.cc b/sql/set_var.cc index d00857a2bc1..3dadc632911 100644 --- a/sql/set_var.cc +++ b/sql/set_var.cc @@ -1255,8 +1255,8 @@ static void fix_tx_isolation(THD *thd, enum_var_type type) thd->variables.tx_isolation); } -static void fix_completion_type(THD *thd __attribute__(unused), - enum_var_type type __attribute__(unused)) {} +static void fix_completion_type(THD *thd __attribute__((unused)), + enum_var_type type __attribute__((unused))) {} static int check_completion_type(THD *thd, set_var *var) { @@ -1295,14 +1295,14 @@ static void fix_net_retry_count(THD *thd, enum_var_type type) thd->net.retry_count=thd->variables.net_retry_count; } #else /* HAVE_REPLICATION */ -static void fix_net_read_timeout(THD *thd __attribute__(unused), - enum_var_type type __attribute__(unused)) +static void fix_net_read_timeout(THD *thd __attribute__((unused)), + enum_var_type type __attribute__((unused))) {} -static void fix_net_write_timeout(THD *thd __attribute__(unused), - enum_var_type type __attribute__(unused)) +static void fix_net_write_timeout(THD *thd __attribute__((unused)), + enum_var_type type __attribute__((unused))) {} -static void fix_net_retry_count(THD *thd __attribute__(unused), - enum_var_type type __attribute__(unused)) +static void fix_net_retry_count(THD *thd __attribute__((unused)), + enum_var_type type __attribute__((unused))) {} #endif /* HAVE_REPLICATION */ diff --git a/sql/slave.cc b/sql/slave.cc index 55cff94a179..28bb7f12008 100644 --- a/sql/slave.cc +++ b/sql/slave.cc @@ -4613,7 +4613,7 @@ static int connect_to_master(THD* thd, MYSQL* mysql, MASTER_INFO* mi, suppress_warnings= 0; sql_print_error("Slave I/O thread: error %s to master \ '%s@%s:%d': \ -Error: '%s' errno: %d retry-time: %d retries: %d", +Error: '%s' errno: %d retry-time: %d retries: %lu", (reconnect ? "reconnecting" : "connecting"), mi->user,mi->host,mi->port, mysql_error(mysql), last_errno, diff --git a/sql/slave.h b/sql/slave.h index c355f7172a9..65adb4564cc 100644 --- a/sql/slave.h +++ b/sql/slave.h @@ -553,7 +553,8 @@ void init_table_rule_array(DYNAMIC_ARRAY* a, bool* a_inited); const char *print_slave_db_safe(const char *db); int check_expected_error(THD* thd, RELAY_LOG_INFO* rli, int error_code); void skip_load_data_infile(NET* net); -void slave_print_error(RELAY_LOG_INFO* rli, int err_code, const char* msg, ...); +void slave_print_error(RELAY_LOG_INFO *rli, int err_code, const char *msg, ...) + ATTRIBUTE_FORMAT(printf, 3, 4); void end_slave(); /* clean up */ void init_master_info_with_options(MASTER_INFO* mi); diff --git a/sql/sql_analyse.cc b/sql/sql_analyse.cc index af9246c673a..62b6d4f7920 100644 --- a/sql/sql_analyse.cc +++ b/sql/sql_analyse.cc @@ -807,9 +807,9 @@ void field_str::get_opt_type(String *answer, ha_rows total_rows) else if (num_info.decimals) // DOUBLE(%d,%d) sometime { if (num_info.dval > -FLT_MAX && num_info.dval < FLT_MAX) - sprintf(buff, "FLOAT(%d,%d)", num_info.integers, num_info.decimals); + sprintf(buff, "FLOAT(%d,%d)", (num_info.integers + num_info.decimals), num_info.decimals); else - sprintf(buff, "DOUBLE(%d,%d)", num_info.integers, num_info.decimals); + sprintf(buff, "DOUBLE(%d,%d)", (num_info.integers + num_info.decimals), num_info.decimals); } else if (ev_num_info.llval >= -128 && ev_num_info.ullval <= @@ -916,10 +916,10 @@ void field_real::get_opt_type(String *answer, else { if (min_arg >= -FLT_MAX && max_arg <= FLT_MAX) - sprintf(buff, "FLOAT(%d,%d)", (int) max_length - (item->decimals + 1), + sprintf(buff, "FLOAT(%d,%d)", (int) max_length - (item->decimals + 1) + max_notzero_dec_len, max_notzero_dec_len); else - sprintf(buff, "DOUBLE(%d,%d)", (int) max_length - (item->decimals + 1), + sprintf(buff, "DOUBLE(%d,%d)", (int) max_length - (item->decimals + 1) + max_notzero_dec_len, max_notzero_dec_len); answer->append(buff, (uint) strlen(buff)); } diff --git a/sql/sql_class.h b/sql/sql_class.h index ccc7a661446..6e1a061f279 100644 --- a/sql/sql_class.h +++ b/sql/sql_class.h @@ -306,7 +306,7 @@ public: const char *log_name); void new_file(bool need_lock); bool write(THD *thd, enum enum_server_command command, - const char *format,...); + const char *format, ...) ATTRIBUTE_FORMAT(printf, 4, 5); bool write(THD *thd, const char *query, uint query_length, time_t query_start=0); bool write(Log_event* event_info); // binary log write diff --git a/sql/stacktrace.c b/sql/stacktrace.c index 43f35c452f7..a2fe2ab88f1 100644 --- a/sql/stacktrace.c +++ b/sql/stacktrace.c @@ -222,7 +222,7 @@ terribly wrong...\n"); fprintf(stderr, "Stack trace seems successful - bottom reached\n"); end: - fprintf(stderr, "Please read http://dev.mysql.com/doc/mysql/en/Using_stack_trace.html and follow instructions on how to resolve the stack trace. Resolved\n\ + fprintf(stderr, "Please read http://dev.mysql.com/doc/mysql/en/using-stack-trace.html and follow instructions on how to resolve the stack trace. Resolved\n\ stack trace is much more helpful in diagnosing the problem, so please do \n\ resolve it\n"); } diff --git a/strings/ctype-big5.c b/strings/ctype-big5.c index 0ca1cf21129..479fb789816 100644 --- a/strings/ctype-big5.c +++ b/strings/ctype-big5.c @@ -6370,6 +6370,7 @@ static MY_CHARSET_HANDLER my_charset_big5_handler= my_strntoull_8bit, my_strntod_8bit, my_strtoll10_8bit, + my_strntoull10rnd_8bit, my_scan_8bit }; diff --git a/strings/ctype-bin.c b/strings/ctype-bin.c index 54c35c82652..0bd5a1fda76 100644 --- a/strings/ctype-bin.c +++ b/strings/ctype-bin.c @@ -517,6 +517,7 @@ static MY_CHARSET_HANDLER my_charset_handler= my_strntoull_8bit, my_strntod_8bit, my_strtoll10_8bit, + my_strntoull10rnd_8bit, my_scan_8bit }; diff --git a/strings/ctype-cp932.c b/strings/ctype-cp932.c index 5f8a93b1c2b..b4e9ba16d92 100644 --- a/strings/ctype-cp932.c +++ b/strings/ctype-cp932.c @@ -5492,6 +5492,7 @@ static MY_CHARSET_HANDLER my_charset_handler= my_strntoull_8bit, my_strntod_8bit, my_strtoll10_8bit, + my_strntoull10rnd_8bit, my_scan_8bit }; diff --git a/strings/ctype-euc_kr.c b/strings/ctype-euc_kr.c index d6df46f7e05..40e0f4e3d2d 100644 --- a/strings/ctype-euc_kr.c +++ b/strings/ctype-euc_kr.c @@ -8711,6 +8711,7 @@ static MY_CHARSET_HANDLER my_charset_handler= my_strntoull_8bit, my_strntod_8bit, my_strtoll10_8bit, + my_strntoull10rnd_8bit, my_scan_8bit }; diff --git a/strings/ctype-eucjpms.c b/strings/ctype-eucjpms.c index 348eb2f6e87..65fef2dfc4c 100644 --- a/strings/ctype-eucjpms.c +++ b/strings/ctype-eucjpms.c @@ -8677,6 +8677,7 @@ static MY_CHARSET_HANDLER my_charset_handler= my_strntoull_8bit, my_strntod_8bit, my_strtoll10_8bit, + my_strntoull10rnd_8bit, my_scan_8bit }; diff --git a/strings/ctype-gb2312.c b/strings/ctype-gb2312.c index 29ecafc3527..c2fc1e2c190 100644 --- a/strings/ctype-gb2312.c +++ b/strings/ctype-gb2312.c @@ -5762,6 +5762,7 @@ static MY_CHARSET_HANDLER my_charset_handler= my_strntoull_8bit, my_strntod_8bit, my_strtoll10_8bit, + my_strntoull10rnd_8bit, my_scan_8bit }; diff --git a/strings/ctype-gbk.c b/strings/ctype-gbk.c index ef1b33fd82c..c4d06d67eb9 100644 --- a/strings/ctype-gbk.c +++ b/strings/ctype-gbk.c @@ -10015,6 +10015,7 @@ static MY_CHARSET_HANDLER my_charset_handler= my_strntoull_8bit, my_strntod_8bit, my_strtoll10_8bit, + my_strntoull10rnd_8bit, my_scan_8bit }; diff --git a/strings/ctype-latin1.c b/strings/ctype-latin1.c index a3f5aec9605..1298b66bb7e 100644 --- a/strings/ctype-latin1.c +++ b/strings/ctype-latin1.c @@ -411,6 +411,7 @@ static MY_CHARSET_HANDLER my_charset_handler= my_strntoull_8bit, my_strntod_8bit, my_strtoll10_8bit, + my_strntoull10rnd_8bit, my_scan_8bit }; diff --git a/strings/ctype-simple.c b/strings/ctype-simple.c index 12ef77c59b1..e40a1948dcf 100644 --- a/strings/ctype-simple.c +++ b/strings/ctype-simple.c @@ -17,6 +17,7 @@ #include <my_global.h> #include "m_string.h" #include "m_ctype.h" +#include "my_sys.h" /* Needed for MY_ERRNO_ERANGE */ #include <errno.h> #include "stdarg.h" @@ -1354,6 +1355,341 @@ longlong my_strtoll10_8bit(CHARSET_INFO *cs __attribute__((unused)), } +#undef ULONGLONG_MAX +/* + Needed under MetroWerks Compiler, since MetroWerks compiler does not + properly handle a constant expression containing a mod operator +*/ +#if defined(__NETWARE__) && defined(__MWERKS__) +static ulonglong ulonglong_max= ~(ulonglong) 0; +#define ULONGLONG_MAX ulonglong_max +#else +#define ULONGLONG_MAX (~(ulonglong) 0) +#endif /* __NETWARE__ && __MWERKS__ */ + + +#define CUTOFF (ULONGLONG_MAX / 10) +#define CUTLIM (ULONGLONG_MAX % 10) +#define DIGITS_IN_ULONGLONG 20 + +static ulonglong d10[DIGITS_IN_ULONGLONG]= +{ + 1, + 10, + 100, + 1000, + 10000, + 100000, + 1000000, + 10000000, + 100000000, + 1000000000, + 10000000000ULL, + 100000000000ULL, + 1000000000000ULL, + 10000000000000ULL, + 100000000000000ULL, + 1000000000000000ULL, + 10000000000000000ULL, + 100000000000000000ULL, + 1000000000000000000ULL, + 10000000000000000000ULL +}; + + +/* + + Convert a string to unsigned long long integer value + with rounding. + + SYNOPSYS + my_strntoull10_8bit() + cs in pointer to character set + str in pointer to the string to be converted + length in string length + unsigned_flag in whether the number is unsigned + endptr out pointer to the stop character + error out returned error code + + DESCRIPTION + This function takes the decimal representation of integer number + from string str and converts it to an signed or unsigned + long long integer value. + Space characters and tab are ignored. + A sign character might precede the digit characters. + The number may have any number of pre-zero digits. + The number may have decimal point and exponent. + Rounding is always done in "away from zero" style: + 0.5 -> 1 + -0.5 -> -1 + + The function stops reading the string str after "length" bytes + or at the first character that is not a part of correct number syntax: + + <signed numeric literal> ::= + [ <sign> ] <exact numeric literal> [ E [ <sign> ] <unsigned integer> ] + + <exact numeric literal> ::= + <unsigned integer> [ <period> [ <unsigned integer> ] ] + | <period> <unsigned integer> + <unsigned integer> ::= <digit>... + + RETURN VALUES + Value of string as a signed/unsigned longlong integer + + endptr cannot be NULL. The function will store the end pointer + to the stop character here. + + The error parameter contains information how things went: + 0 ok + ERANGE If the the value of the converted number is out of range + In this case the return value is: + - ULONGLONG_MAX if unsigned_flag and the number was too big + - 0 if unsigned_flag and the number was negative + - LONGLONG_MAX if no unsigned_flag and the number is too big + - LONGLONG_MIN if no unsigned_flag and the number it too big negative + + EDOM If the string didn't contain any digits. + In this case the return value is 0. +*/ + +ulonglong +my_strntoull10rnd_8bit(CHARSET_INFO *cs __attribute__((unused)), + const char *str, uint length, int unsigned_flag, + char **endptr, int *error) +{ + const char *dot, *end9, *beg, *end= str + length; + ulonglong ull; + ulong ul; + unsigned char ch; + int shift= 0, digits= 0, negative, addon; + + /* Skip leading spaces and tabs */ + for ( ; str < end && (*str == ' ' || *str == '\t') ; str++); + + if (str >= end) + goto ret_edom; + + if ((negative= (*str == '-')) || *str=='+') /* optional sign */ + { + if (++str == end) + goto ret_edom; + } + + beg= str; + end9= (str + 9) > end ? end : (str + 9); + /* Accumulate small number into ulong, for performance purposes */ + for (ul= 0 ; str < end9 && (ch= (unsigned char) (*str - '0')) < 10; str++) + { + ul= ul * 10 + ch; + } + + if (str >= end) /* Small number without dots and expanents */ + { + *endptr= (char*) str; + if (negative) + { + if (unsigned_flag) + { + *error= ul ? MY_ERRNO_ERANGE : 0; + return 0; + } + else + { + *error= 0; + return (ulonglong) (longlong) (long) -ul; + } + } + else + { + *error=0; + return (ulonglong) ul; + } + } + + digits= str - beg; + + /* Continue to accumulate into ulonglong */ + for (dot= NULL, ull= ul; str < end; str++) + { + if ((ch= (unsigned char) (*str - '0')) < 10) + { + if (ull < CUTOFF || (ull == CUTOFF && ch <= CUTLIM)) + { + ull= ull * 10 + ch; + digits++; + continue; + } + /* + Adding the next digit would overflow. + Remember the next digit in "addon", for rounding. + Scan all digits with an optional single dot. + */ + if (ull == CUTOFF) + { + ull= ULONGLONG_MAX; + addon= 1; + str++; + } + else + addon= (*str >= '5'); + for ( ; str < end && (ch= (unsigned char) (*str - '0')) < 10; str++) + { + if (!dot) + shift++; + } + if (str < end && *str == '.' && !dot) + { + str++; + for ( ; str < end && (ch= (unsigned char) (*str - '0')) < 10; str++); + } + goto exp; + } + + if (*str == '.') + { + if (dot) + { + /* The second dot character */ + addon= 0; + goto exp; + } + else + { + dot= str + 1; + } + continue; + } + + /* Unknown character, exit the loop */ + break; + } + shift= dot ? dot - str : 0; /* Right shift */ + addon= 0; + +exp: /* [ E [ <sign> ] <unsigned integer> ] */ + + if (!digits) + { + str= beg; + goto ret_edom; + } + + if (str < end && (*str == 'e' || *str == 'E')) + { + str++; + if (str < end) + { + int negative_exp, exp; + if ((negative_exp= (*str == '-')) || *str=='+') + { + if (++str == end) + goto ret_sign; + } + for (exp= 0 ; + str < end && (ch= (unsigned char) (*str - '0')) < 10; + str++) + { + exp= exp * 10 + ch; + } + shift+= negative_exp ? -exp : exp; + } + } + + if (shift == 0) /* No shift, check addon digit */ + { + if (addon) + { + if (ull == ULONGLONG_MAX) + goto ret_too_big; + ull++; + } + goto ret_sign; + } + + if (shift < 0) /* Right shift */ + { + ulonglong d, r; + + if (-shift >= DIGITS_IN_ULONGLONG) + goto ret_zero; /* Exponent is a big negative number, return 0 */ + + d= d10[-shift]; + r= (ull % d) * 2; + ull /= d; + if (r >= d) + ull++; + goto ret_sign; + } + + if (shift > DIGITS_IN_ULONGLONG) /* Huge left shift */ + { + if (!ull) + goto ret_sign; + goto ret_too_big; + } + + for ( ; shift > 0; shift--, ull*= 10) /* Left shift */ + { + if (ull > CUTOFF) + goto ret_too_big; /* Overflow, number too big */ + } + +ret_sign: + *endptr= (char*) str; + + if (!unsigned_flag) + { + if (negative) + { + if (ull > (ulonglong) LONGLONG_MIN) + { + *error= MY_ERRNO_ERANGE; + return (ulonglong) LONGLONG_MIN; + } + *error= 0; + return (ulonglong) -ull; + } + else + { + if (ull > (ulonglong) LONGLONG_MAX) + { + *error= MY_ERRNO_ERANGE; + return (ulonglong) LONGLONG_MAX; + } + *error= 0; + return ull; + } + } + + /* Unsigned number */ + if (negative && ull) + { + *error= MY_ERRNO_ERANGE; + return 0; + } + *error= 0; + return ull; + +ret_zero: + *endptr= (char*) str; + *error= 0; + return 0; + +ret_edom: + *endptr= (char*) str; + *error= MY_ERRNO_EDOM; + return 0; + +ret_too_big: + *endptr= (char*) str; + *error= MY_ERRNO_ERANGE; + return unsigned_flag ? + ULONGLONG_MAX : + negative ? (ulonglong) LONGLONG_MIN : (ulonglong) LONGLONG_MAX; +} + + /* Check if a constant can be propagated @@ -1434,6 +1770,7 @@ MY_CHARSET_HANDLER my_charset_8bit_handler= my_strntoull_8bit, my_strntod_8bit, my_strtoll10_8bit, + my_strntoull10rnd_8bit, my_scan_8bit }; diff --git a/strings/ctype-sjis.c b/strings/ctype-sjis.c index 57d6d8bae2b..3854837e09a 100644 --- a/strings/ctype-sjis.c +++ b/strings/ctype-sjis.c @@ -4663,6 +4663,7 @@ static MY_CHARSET_HANDLER my_charset_handler= my_strntoull_8bit, my_strntod_8bit, my_strtoll10_8bit, + my_strntoull10rnd_8bit, my_scan_8bit }; diff --git a/strings/ctype-tis620.c b/strings/ctype-tis620.c index dc4f18b516b..85ebbe82731 100644 --- a/strings/ctype-tis620.c +++ b/strings/ctype-tis620.c @@ -891,6 +891,7 @@ static MY_CHARSET_HANDLER my_charset_handler= my_strntoull_8bit, my_strntod_8bit, my_strtoll10_8bit, + my_strntoull10rnd_8bit, my_scan_8bit }; diff --git a/strings/ctype-ucs2.c b/strings/ctype-ucs2.c index 97dca79e84b..4a60220f73e 100644 --- a/strings/ctype-ucs2.c +++ b/strings/ctype-ucs2.c @@ -974,6 +974,35 @@ double my_strntod_ucs2(CHARSET_INFO *cs __attribute__((unused)), } +ulonglong my_strntoull10rnd_ucs2(CHARSET_INFO *cs __attribute__((unused)), + const char *nptr, uint length, int unsign_fl, + char **endptr, int *err) +{ + char buf[256], *b= buf; + ulonglong res; + const uchar *end, *s= (const uchar*) nptr; + my_wc_t wc; + int cnv; + + /* Cut too long strings */ + if (length >= sizeof(buf)) + length= sizeof(buf)-1; + end= s + length; + + while ((cnv= cs->cset->mb_wc(cs,&wc,s,end)) > 0) + { + s+= cnv; + if (wc > (int) (uchar) 'e' || !wc) + break; /* Can't be a number part */ + *b++= (char) wc; + } + + res= my_strntoull10rnd_8bit(cs, buf, b - buf, unsign_fl, endptr, err); + *endptr= (char*) nptr + 2 * (uint) (*endptr- buf); + return res; +} + + /* This is a fast version optimized for the case of radix 10 / -10 */ @@ -1629,6 +1658,7 @@ MY_CHARSET_HANDLER my_charset_ucs2_handler= my_strntoull_ucs2, my_strntod_ucs2, my_strtoll10_ucs2, + my_strntoull10rnd_ucs2, my_scan_ucs2 }; diff --git a/strings/ctype-ujis.c b/strings/ctype-ujis.c index ca27b4bef6b..675ac918e2c 100644 --- a/strings/ctype-ujis.c +++ b/strings/ctype-ujis.c @@ -8545,6 +8545,7 @@ static MY_CHARSET_HANDLER my_charset_handler= my_strntoull_8bit, my_strntod_8bit, my_strtoll10_8bit, + my_strntoull10rnd_8bit, my_scan_8bit }; diff --git a/strings/ctype-utf8.c b/strings/ctype-utf8.c index 3594ab954c6..3a5c01a2861 100644 --- a/strings/ctype-utf8.c +++ b/strings/ctype-utf8.c @@ -2548,6 +2548,7 @@ MY_CHARSET_HANDLER my_charset_utf8_handler= my_strntoull_8bit, my_strntod_8bit, my_strtoll10_8bit, + my_strntoull10rnd_8bit, my_scan_8bit }; diff --git a/strings/strtod.c b/strings/strtod.c index 7171a6e0801..ddb570718a0 100644 --- a/strings/strtod.c +++ b/strings/strtod.c @@ -30,7 +30,8 @@ #include "m_ctype.h" #define MAX_DBL_EXP 308 -#define MAX_RESULT_FOR_MAX_EXP 1.79769313486232 +#define MAX_RESULT_FOR_MAX_EXP 1.7976931348623157 +#define MIN_RESULT_FOR_MIN_EXP 2.225073858507202 static double scaler10[] = { 1.0, 1e10, 1e20, 1e30, 1e40, 1e50, 1e60, 1e70, 1e80, 1e90 }; @@ -57,10 +58,11 @@ double my_strtod(const char *str, char **end_ptr, int *error) { double result= 0.0; uint negative= 0, ndigits, dec_digits= 0, neg_exp= 0; - int exp= 0, digits_after_dec_point= 0; + int exp= 0, digits_after_dec_point= 0, tmp_exp; const char *old_str, *end= *end_ptr, *start_of_number; char next_char; my_bool overflow=0; + double scaler= 1.0; *error= 0; if (str >= end) @@ -91,6 +93,7 @@ double my_strtod(const char *str, char **end_ptr, int *error) while ((next_char= *str) >= '0' && next_char <= '9') { result= result*10.0 + (next_char - '0'); + scaler= scaler*10.0; if (++str == end) { next_char= 0; /* Found end of string */ @@ -114,6 +117,7 @@ double my_strtod(const char *str, char **end_ptr, int *error) { result= result*10.0 + (next_char - '0'); digits_after_dec_point++; + scaler= scaler*10.0; if (++str == end) { next_char= 0; @@ -144,39 +148,54 @@ double my_strtod(const char *str, char **end_ptr, int *error) } while (str < end && my_isdigit(&my_charset_latin1, *str)); } } - if ((exp= (neg_exp ? exp + digits_after_dec_point : - exp - digits_after_dec_point))) + tmp_exp= neg_exp ? exp + digits_after_dec_point : exp - digits_after_dec_point; + if (tmp_exp) { - double scaler; - if (exp < 0) - { - exp= -exp; - neg_exp= 1; /* neg_exp was 0 before */ - } - if (exp + ndigits >= MAX_DBL_EXP + 1 && result) + int order; + /* + Check for underflow/overflow. + order is such an integer number that f = C * 10 ^ order, + where f is the resulting floating point number and 1 <= C < 10. + Here we compute the modulus + */ + order= exp + (neg_exp ? -1 : 1) * (ndigits - 1); + if (order < 0) + order= -order; + if (order >= MAX_DBL_EXP && result) { - /* - This is not 100 % as we actually will give an owerflow for - 17E307 but not for 1.7E308 but lets cut some corners to make life - simpler - */ - if (exp + ndigits > MAX_DBL_EXP + 1 || - result >= MAX_RESULT_FOR_MAX_EXP) + double c; + /* Compute modulus of C (see comment above) */ + c= result / scaler * 10.0; + if (neg_exp) { - if (neg_exp) + if (order > MAX_DBL_EXP || c < MIN_RESULT_FOR_MIN_EXP) + { result= 0.0; - else + goto done; + } + } + else + { + if (order > MAX_DBL_EXP || c > MAX_RESULT_FOR_MAX_EXP) + { overflow= 1; - goto done; + goto done; + } } } - scaler= 1.0; + + exp= tmp_exp; + if (exp < 0) + { + exp= -exp; + neg_exp= 1; /* neg_exp was 0 before */ + } while (exp >= 100) { - scaler*= 1.0e100; + result= neg_exp ? result/1.0e100 : result*1.0e100; exp-= 100; } - scaler*= scaler10[exp/10]*scaler1[exp%10]; + scaler= scaler10[exp/10]*scaler1[exp%10]; if (neg_exp) result/= scaler; else diff --git a/zlib/Makefile.am b/zlib/Makefile.am index 0081c93a2ae..af7d60d8568 100644 --- a/zlib/Makefile.am +++ b/zlib/Makefile.am @@ -18,6 +18,8 @@ INCLUDES= -I$(top_builddir)/include -I$(top_srcdir)/include +LIBS= $(NON_THREADED_LIBS) + pkglib_LTLIBRARIES=libz.la libz_la_LDFLAGS= -version-info 3:3:2 |