/** * Help to build query to be sent to server. * Append column declaration to the query. * Only for TDS 7.0+. * \tds * \param[out] clause output string * \param bcpcol column to append * \param first true if column is the first * \return TDS_SUCCESS or TDS_FAIL. */ static TDSRET tds7_build_bulk_insert_stmt(TDSSOCKET * tds, TDSPBCB * clause, TDSCOLUMN * bcpcol, int first) { char column_type[40]; tdsdump_log(TDS_DBG_FUNC, "tds7_build_bulk_insert_stmt(%p, %p, %p, %d)\n", tds, clause, bcpcol, first); if (TDS_FAILED(tds_get_column_declaration(tds, bcpcol, column_type))) { tdserror(tds_get_ctx(tds), tds, TDSEBPROBADTYP, errno); tdsdump_log(TDS_DBG_FUNC, "error: cannot build bulk insert statement. unrecognized server datatype %d\n", bcpcol->on_server.column_type); return TDS_FAIL; } if (clause->cb < strlen(clause->pb) + tds_quote_id(tds, NULL, tds_dstr_cstr(&bcpcol->column_name), tds_dstr_len(&bcpcol->column_name)) + strlen(column_type) + ((first) ? 2u : 4u)) { char *temp = (char*) malloc(2 * clause->cb); if (!temp) { tdserror(tds_get_ctx(tds), tds, TDSEMEM, errno); return TDS_FAIL; } strcpy(temp, clause->pb); if (clause->from_malloc) free(clause->pb); clause->from_malloc = 1; clause->pb = temp; clause->cb *= 2; } if (!first) strcat(clause->pb, ", "); tds_quote_id(tds, strchr(clause->pb, 0), tds_dstr_cstr(&bcpcol->column_name), tds_dstr_len(&bcpcol->column_name)); strcat(clause->pb, " "); strcat(clause->pb, column_type); return TDS_SUCCESS; }
bool pool_user_send_login_ack(TDS_POOL * pool, TDS_POOL_USER * puser) { char msg[256]; char block[32]; TDSSOCKET *tds = puser->sock.tds, *mtds = puser->assigned_member->sock.tds; TDSLOGIN *login = puser->login; const char *database; const char *server = mtds->conn->server ? mtds->conn->server : "JDBC"; bool dbname_mismatch, odbc_mismatch; pool->user_logins++; /* copy a bit of information, resize socket with block */ tds->conn->tds_version = mtds->conn->tds_version; tds->conn->product_version = mtds->conn->product_version; memcpy(tds->conn->collation, mtds->conn->collation, sizeof(tds->conn->collation)); tds->conn->tds71rev1 = mtds->conn->tds71rev1; free(tds->conn->product_name); tds->conn->product_name = strdup(mtds->conn->product_name); tds_realloc_socket(tds, mtds->conn->env.block_size); tds->conn->env.block_size = mtds->conn->env.block_size; tds->conn->client_spid = mtds->conn->spid; /* if database is different use USE statement */ database = pool->database; dbname_mismatch = !tds_dstr_isempty(&login->database) && strcasecmp(tds_dstr_cstr(&login->database), database) != 0; odbc_mismatch = (login->option_flag2 & TDS_ODBC_ON) == 0; if (dbname_mismatch || odbc_mismatch) { char *str; int len = 128 + tds_quote_id(mtds, NULL, tds_dstr_cstr(&login->database),-1); TDSRET ret; if ((str = (char *) malloc(len)) == NULL) return false; str[0] = 0; /* swicth to dblib options */ if (odbc_mismatch) strcat(str, "SET ANSI_DEFAULTS OFF\nSET CONCAT_NULL_YIELDS_NULL OFF\n"); if (dbname_mismatch) { strcat(str, "USE "); tds_quote_id(mtds, strchr(str, 0), tds_dstr_cstr(&login->database), -1); } ret = tds_submit_query(mtds, str); free(str); if (TDS_FAILED(ret) || TDS_FAILED(tds_process_simple_query(mtds))) return false; if (dbname_mismatch) database = tds_dstr_cstr(&login->database); else database = mtds->conn->env.database; } // 7.0 // env database // database change message (with server name correct) // env language // language change message // env 0x3 charset ("iso_1") // env 0x5 lcid ("1033") // env 0x6 ("196609" ?? 0x30001) // loginack // env 0x4 packet size // done // // 7.1/7.2/7.3 // env database // database change message (with server name correct) // env 0x7 collation // env language // language change message // loginack // env 0x4 packet size // done tds->out_flag = TDS_REPLY; tds_env_change(tds, TDS_ENV_DATABASE, "master", database); sprintf(msg, "Changed database context to '%s'.", database); tds_send_msg(tds, 5701, 2, 0, msg, server, NULL, 1); if (!login->suppress_language) { tds_env_change(tds, TDS_ENV_LANG, NULL, "us_english"); tds_send_msg(tds, 5703, 1, 0, "Changed language setting to 'us_english'.", server, NULL, 1); } if (IS_TDS71_PLUS(tds->conn)) { tds_put_byte(tds, TDS_ENVCHANGE_TOKEN); tds_put_smallint(tds, 8); tds_put_byte(tds, TDS_ENV_SQLCOLLATION); tds_put_byte(tds, 5); tds_put_n(tds, tds->conn->collation, 5); tds_put_byte(tds, 0); } tds_send_login_ack(tds, mtds->conn->product_name); sprintf(block, "%d", tds->conn->env.block_size); tds_env_change(tds, TDS_ENV_PACKSIZE, block, block); /* tds_send_capabilities_token(tds); */ tds_send_done_token(tds, 0, 0); /* send it! */ tds_flush_packet(tds); tds_free_login(login); puser->login = NULL; return true; }