Skip to Content.
Sympa Menu

freetds - Fix for: "The token datastream length was not correct. This is an internal protocol error."

freetds AT lists.ibiblio.org

Subject: FreeTDS Development Group

List archive

Chronological Thread  
  • From: Fabien Roy <froy AT singleentry.com>
  • To: "TDS Development Group" <freetds AT franklin.oit.unc.edu>
  • Subject: Fix for: "The token datastream length was not correct. This is an internal protocol error."
  • Date: Thu, 21 Dec 2000 18:50:29 -0600


Hi,

I have some fixes for the tds:
Added "gethostbyaddr" so the interface file can use either ip
(x.x.x.x) or host name.
Added support for extended numeric precision supported by ASE 12.5
beta (Linux).
Fixed the socket write code (this got rid of the error:"The token
datastream length was not correct. This is an internal protocol
error.")
Finally I made the tds source code ANSI-C compliant, i.e. functions
which are declared to return a value are now returning value and also
some explicit castings.
I also commented out unused variables (I love no-warning compile :-)

TODO: Adding support for TDS_LONGCHAR
Here are the diffs:

########################################
diff -bBdu tds.old/convert.c tds.new/convert.c
--- tds.old/convert.c Thu Dec 21 17:13:31 2000
+++ tds.new/convert.c Thu Dec 21 17:23:32 2000
@@ -57,7 +57,7 @@
it's not thread safe
it works for the moment though til i decide how i really want to
handle it
*/
-static TDS_CHAR tmp_str[1024];
+static TDS_CHAR tmp_str[4096];


int tds_get_conversion_type(int srctype, int colsize)
@@ -105,7 +105,9 @@
dest[cplen]='\0';
return cplen;
}
+ return 0;
}
+
static TDS_UINT utf16len(const utf16_t* s)
{
const utf16_t* p = s;
@@ -195,6 +197,7 @@
memcpy(varbin->array, src, cplen);
return sizeof(TDS_VARBINARY);
}
+ return 0;
}

TDS_INT tds_convert_char(int srctype,unsigned char *src,
@@ -390,12 +393,15 @@
}
return tds_convert_any(dest, desttype, destlen, &any);
}
+
+extern char *tds_numeric_to_string(TDS_NUMERIC *numeric, char *s);
+
TDS_INT tds_convert_numeric(int srctype,TDS_NUMERIC *src,TDS_INT srclen,
int desttype,unsigned char
*dest,TDS_INT destlen)
{
- unsigned long bignum;
+ //unsigned long bignum;
char tmpstr[MAXPRECISION];
- int left_len;
+ //int left_len;

TDS_FLOAT d;

switch(desttype) {
@@ -419,7 +425,9 @@
return TDS_FAIL;
break;
}
+ return TDS_FAIL;
}
+
TDS_INT tds_convert_money4(int srctype,unsigned char *src, int srclen,
int desttype,unsigned char *dest,TDS_INT
destlen)
{
@@ -458,6 +466,9 @@
}
return sizeof(TDS_MONEY4);
}
+
+extern char *tds_money_to_string(TDS_MONEY *money, char *s);
+
TDS_INT tds_convert_money(int srctype,unsigned char *src,
int desttype,unsigned char *dest,TDS_INT
destlen)
{
@@ -468,7 +479,7 @@
switch(desttype) {
case SYBCHAR:
case SYBVARCHAR:
- return tds_money_to_string(src, dest);
+ return (int)tds_money_to_string((TDS_MONEY *)src, dest);
break;
case SYBFLT8:
/* Used memcpy to avoid alignment/bus errors */
@@ -485,6 +496,7 @@
return TDS_FAIL;
break;
}
+ return TDS_FAIL;
}
TDS_INT tds_convert_datetime(int srctype,unsigned char *src,int
desttype,unsigned char *dest,TDS_INT destlen)
{
@@ -527,7 +539,9 @@
return TDS_FAIL;
break;
}
+ return TDS_FAIL;
}
+
TDS_INT tds_convert_datetime4(int srctype,unsigned char *src,int
desttype,unsigned char *dest,TDS_INT destlen)
{
TDS_USMALLINT days, minutes;
@@ -568,6 +582,7 @@
return TDS_FAIL;
break;
}
+ return TDS_FAIL;
}

TDS_INT tds_convert_real(int srctype,unsigned char *src,int
desttype,unsigned
diff -bBdu tds.old/login.c tds.new/login.c
--- tds.old/login.c Thu Dec 21 17:13:51 2000
+++ tds.new/login.c Thu Dec 21 17:24:03 2000
@@ -260,7 +261,7 @@

unsigned char magic42[]= {0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00};
unsigned char magic50[]= {0x00,0x00,0x00,0x00};
- unsigned char capabilities[]=
{0x01,0x07,0x03,109,127,0xFF,0xFF,0xFF,0xFE,0x02,0x07,0x00,0x00,0x0A,104,0x00,0x00,0x00};
+ // unsigned char capabilities[]=
{0x01,0x07,0x03,109,127,0xFF,0xFF,0xFF,0xFE,0x02,0x07,0x00,0x00,0x0A,104,0x00,0x00,0x00};
/*
** This is the original capabilities packet we were working with
(sqsh)
unsigned char capabilities[]=
{0x01,0x07,0x03,109,127,0xFF,0xFF,0xFF,0xFE,0x02,0x07,0x00,0x00,0x0A,104,0x00,0x00,0x00};
@@ -316,7 +317,7 @@
if (IS_TDS42(tds)) {
rc|=tds_put_string(tds,login->password,255);
} else {
-
sprintf(passwdstr,"%c%c%s",0,strlen(login->password),login->password);
+ sprintf(passwdstr,"%c%c%s",0,(unsigned
char)strlen(login->password),login->password);

rc|=tds_put_buf(tds,passwdstr,255,strlen(login->password)+2);
}

@@ -351,6 +352,7 @@
rc|=tds_flush_packet(tds);
/* get_incoming(tds->s); */

+ return 0;
}


/*
@@ -360,9 +362,12 @@
int tds7_send_login(TDSSOCKET *tds, TDSLOGIN *login)
{
int rc;
- unsigned char magic1[] =
{6,0x83,0xf2,0xf8,0xff,0x0,0x0,0x0,0x0,0xe0,0x03,0x0,0x0,0x88,0xff,0xff,0xff,0x36,0x04,0x00,0x00};
+ unsigned char magic1[] = {
+ 6,0x83,0xf2,0xf8,0xff,0x0,0x0,0x0,0x0,
+ 0xe0,0x03,0x0,0x0,0x88,0xff,0xff,0xff,
+ 0x36,0x04,0x00,0x00};
unsigned char magic2[] = {0x00,0x40,0x33,0x9a,0x6b,0x50};
- /* 0xb4,0x00,0x30,0x00,0xe4,0x00,0x00,0x00}; */
+ /* {0xb4,0x00,0x30,0x00,0xe4,0x00,0x00,0x00}; */
unsigned char magic3[] = "NTLMSSP";
unsigned char unicode_string[255];
int packet_size;
@@ -448,6 +453,7 @@
tds_put_n(tds,NULL,3);

rc|=tds_flush_packet(tds);
+ return 0;
}

/*
diff -bBdu tds.old/mem.c tds.new/mem.c
--- tds.old/mem.c Thu Dec 21 17:14:06 2000
+++ tds.new/mem.c Thu Dec 21 17:24:15 2000
@@ -38,7 +38,7 @@
TDSPARAMINFO *tds_alloc_param_result(TDSPARAMINFO *old_param)
{
TDSPARAMINFO *param_info;
- int col;
+ //int col;

if (!old_param) {
param_info = (TDSPARAMINFO *) malloc(sizeof(TDSPARAMINFO));
@@ -122,11 +122,11 @@
for (i=0;i<param_info->num_cols;i++)
{
if(param_info->columns[i])
- free(param_info->columns[i]);
+ FREE(param_info->columns[i]);
}
- if (param_info->num_cols) free(param_info->columns);
- if (param_info->current_row) free(param_info->current_row);
- free(param_info);
+ if (param_info->num_cols) FREE(param_info->columns);
+ if (param_info->current_row) FREE(param_info->current_row);
+ FREE(param_info);
}
}
void tds_free_compute_results(TDSCOMPUTEINFO *comp_info)
@@ -138,11 +138,11 @@
for (i=0;i<comp_info->num_cols;i++)
{
if(comp_info->columns[i])
- free(comp_info->columns[i]);
+ FREE(comp_info->columns[i]);
}
- if (comp_info->num_cols) free(comp_info->columns);
- if (comp_info->current_row) free(comp_info->current_row);
- free(comp_info);
+ if (comp_info->num_cols) FREE(comp_info->columns);
+ if (comp_info->current_row) FREE(comp_info->current_row);
+ FREE(comp_info);
}
}

@@ -153,14 +153,14 @@

if(res_info)
{
- if (res_info->current_row) free(res_info->current_row);
+ if (res_info->current_row) FREE(res_info->current_row);
for (i=0;i<res_info->num_cols;i++)
{
if(res_info->columns[i])
tds_free_column(res_info->columns[i]);
}
- if (res_info->num_cols) free(res_info->columns);
- free(res_info);
+ if (res_info->num_cols) FREE(res_info->columns);
+ FREE(res_info);
}

}
@@ -175,8 +175,8 @@
}
void tds_free_column(TDSCOLINFO *column)
{
- if (column->column_textvalue) free(column->column_textvalue);
- free(column);
+ if (column->column_textvalue) FREE(column->column_textvalue);
+ FREE(column);
}
TDSLOGIN *tds_alloc_login()
{
@@ -220,7 +220,7 @@
}
void tds_free_login(TDSLOGIN *login)
{
- if (login) free(login);
+ if (login) FREE(login);
}
TDSSOCKET *tds_alloc_socket(int bufsize)
{
@@ -248,11 +248,11 @@
if (tds) {
tds_free_all_results(tds);
tds_free_env(tds);
- if (tds->msg_info) free(tds->msg_info);
- if (tds->in_buf) free(tds->in_buf);
- if (tds->out_buf) free(tds->out_buf);
+ if (tds->msg_info) FREE(tds->msg_info);
+ if (tds->in_buf) FREE(tds->in_buf);
+ if (tds->out_buf) FREE(tds->out_buf);
if (tds->s) close(tds->s);
- free(tds);
+ FREE(tds);
}
}
TDSENVINFO *tds_alloc_env(TDSSOCKET *tds)
@@ -269,20 +269,20 @@
{
if (tds->env) {
if (tds->env->language)
- free(tds->env->language);
+ FREE(tds->env->language);
if (tds->env->charset)
- free(tds->env->charset);
+ FREE(tds->env->charset);
if (tds->env->database)
- free(tds->env->database);
+ FREE(tds->env->database);
}
}
void tds_free_msg(TDSMSGINFO *msg_info)
{
if (msg_info) {
- if(msg_info->message) free(msg_info->message);
- if(msg_info->server) free(msg_info->server);
- if(msg_info->proc_name) free(msg_info->proc_name);
- if(msg_info->sql_state) free(msg_info->sql_state);
+ if(msg_info->message) FREE(msg_info->message);
+ if(msg_info->server) FREE(msg_info->server);
+ if(msg_info->proc_name) FREE(msg_info->proc_name);
+ if(msg_info->sql_state) FREE(msg_info->sql_state);
}
}
int tds_add_connection(TDSCONTEXT *ctx, TDSSOCKET *tds)
diff -bBdu tds.old/numeric.c tds.new/numeric.c
--- tds.old/numeric.c Thu Dec 21 17:14:28 2000
+++ tds.new/numeric.c Thu Dec 21 17:24:37 2000
@@ -21,7 +21,7 @@
#include <stdio.h>

/*
-** these routines use arrays of unsigned char to handle arbitrary
+ ** these routines use arrays of unsigned char to handle arbitrary
** precision numbers. All-in-all it's probably pretty slow, but it
** does work. I just heard of a GNU lib for arb. precision math, so
** that might be an option in the future.
@@ -37,10 +37,16 @@
** precision (with the sign).
*/
int g__numeric_bytes_per_prec[] =
-{2, 2, 3, 3, 4, 4, 4, 5, 5, 6, 6, 6, 7, 7, 8, 8, 9, 9, 9,
- 10, 10, 11, 11, 11, 12, 12, 13, 13, 14, 14, 14, 15, 15,
- 16, 16, 16, 17, 17, 18, 18, 19, 19, 19, 20, 20, 21, 21, 21,
- 22, 22, 23, 23, 24, 24, 24, 25, 25, 26, 26, 26};
+{
+ -1, 2, 2, 3, 3, 4, 4, 4, 5, 5,
+ 6, 6, 6, 7, 7, 8, 8, 9, 9, 9,
+ 10, 10, 11, 11, 11, 12, 12, 13, 13, 14,
+ 14, 14, 15, 15, 16, 16, 16, 17, 17, 18,
+ 18, 19, 19, 19, 20, 20, 21, 21, 21, 22,
+ 22, 23, 23, 24, 24, 24, 25, 25, 26, 26,
+ 26, 27, 27, 28, 28, 28, 29, 29, 30, 30,
+ 31, 31, 31, 32, 32, 33, 33, 33
+};



@@ -52,9 +58,12 @@
unsigned char multiplier[MAXPRECISION], temp[MAXPRECISION];
unsigned char product[MAXPRECISION];
unsigned char *number;
- unsigned char reorder[8];
+ // unsigned char reorder[8];
int num_bytes = 8;
- int i, top, pos, neg=0;
+ int i;
+ // int top;
+ int pos;
+ int neg=0;

memset(multiplier,0,MAXPRECISION);
memset(product,0,MAXPRECISION);
@@ -108,14 +117,15 @@
unsigned char product[MAXPRECISION];
unsigned char *number;
int num_bytes;
- int i, top, pos;
+ // int i;
+ // int top;
+ int pos;

memset(multiplier,0,MAXPRECISION);
memset(product,0,MAXPRECISION);
multiplier[0]=1;
number = numeric->array;
- num_bytes = g__numeric_bytes_per_prec[numeric->precision-1];
-
+ num_bytes = g__numeric_bytes_per_prec[numeric->precision];
if (numeric->array[0] == 1)
*s++ = '-';

@@ -180,4 +190,5 @@
s[j++]=array[i]+'0';
}
s[j]='\0';
+ return s;
}
diff -bBdu tds.old/read.c tds.new/read.c
--- tds.old/read.c Thu Dec 21 17:35:06 2000
+++ tds.new/read.c Thu Dec 21 17:36:36 2000
@@ -170,7 +169,7 @@
temp = (char *) malloc(need*2);
tds_get_n(tds,temp,need*2);
tds7_unicode2ascii(temp,dest,need);
- free(temp);
+ FREE(temp);
return(dest);

} else {
diff -bBdu tds.old/tds.h tds.new/tds.h
--- tds.old/tds.h Thu Dec 21 17:15:41 2000
+++ tds.new/tds.h Thu Dec 21 18:31:15 2000
@@ -49,7 +49,9 @@
#include <string.h>
#include <stdlib.h>
#include <time.h>
+#ifndef __APPLE__
#include <malloc.h>
+#endif

#include <sys/time.h>
#endif

diff -bBdu tds.old/tdsutil.h tds.new/tdsutil.h
--- tds.old/tdsutil.h Thu Dec 21 17:19:45 2000
+++ tds.new/tdsutil.h Thu Dec 21 17:53:40 2000
@@ -83,3 +83,5 @@

#endif

+#define FREE(x) {free((x)); (x) = NULL;}
+
Only in tds.new: tdsver.h
diff -bBdu tds.old/token.c tds.new/token.c
--- tds.old/token.c Thu Dec 21 17:20:35 2000
+++ tds.new/token.c Thu Dec 21 17:27:10 2000
@@ -25,11 +25,11 @@
no_unused_var_warn};

/*
-** All these functions process the input from the wire so it
+ ** All these functions process the input from the wire so it
** may be used by the upper level functions.
*/

-static unsigned char seq=0;
+//static unsigned char seq=0;
int (*g_tds_msg_handler)() = NULL;
int (*g_tds_err_handler)() = NULL;

@@ -46,11 +46,12 @@
static int tds_process_param_result_tokens(TDSSOCKET *tds);

/*
- ** The following little table is indexed by precision-1 and will
+ ** The following little table is indexed by precision and will
** tell us the number of bytes required to store the specified
** precision.
*/
extern int g__numeric_bytes_per_prec[];
+extern TDS_INT tds_get_int(TDSSOCKET *tds);


/*
@@ -59,7 +60,7 @@
*/
int tds_process_default_tokens(TDSSOCKET *tds, int marker)
{
- TDSRESULTINFO *info;
+ // TDSRESULTINFO *info;
int order_len;
int tok_size;
int more_results;
@@ -163,7 +164,7 @@
int len;
unsigned char major_ver, minor_ver;
unsigned char ack;
- char *tmpbuf;
+ // char *tmpbuf;

tdsdump_log("%L inside tds_process_login_tokens()\n");
/* get_incoming(tds->s); */
@@ -186,7 +187,7 @@
tmpbuf = (char *) malloc(len);
tds_get_n(tds, tmpbuf, len);
tdsdump_log("%L login ack marker = %d\n%D\n", marker,
tmpbuf, len);
- free(tmpbuf);
+ FREE(tmpbuf);
*/
/* TDS 5.0 reports 5 on success 6 on failure
** TDS 4.2 reports 1 on success and is not
@@ -296,7 +297,7 @@
}

/*
-** tds_process_row_tokens() is called once a result set has been obtained
+ ** tds_process_row_tokens() is called once a result set has been
obtained
** with tds_process_result_tokens(). It calls tds_process_row() to copy
** data into the row buffer.
*/
@@ -340,7 +341,7 @@
}

/*
-** tds_process_col_name() is one half of the result set under TDS 4.2
+ ** tds_process_col_name() is one half of the result set under TDS 4.2
** it contains all the column names, a TDS_COLINFO_TOKEN should
** immediately follow this token with the datatype/size information
** This is a 4.2 only function
@@ -396,14 +397,14 @@
strncpy(curcol->column_name, cur->column_name,
sizeof(curcol->column_name));
prev=cur; cur=cur->next;
- free(prev->column_name);
- free(prev);
+ FREE(prev->column_name);
+ FREE(prev);
}
return TDS_SUCCEED;
}

/*
-** tds_process_col_info() is the other half of result set processing
+ ** tds_process_col_info() is the other half of result set processing
** under TDS 4.2. It follows tds_process_col_name(). It contains all the
** column type and size information.
** This is a 4.2 only function
@@ -757,7 +758,7 @@
{
int colsize, i, j, sign, num_pos;
unsigned char b_val;
- unsigned char junk[17];
+ // unsigned char junk[17];
TDSCOLINFO *curcol;
TDSRESULTINFO *info;
unsigned char *dest;
@@ -843,7 +844,7 @@
sign = tds_get_byte(tds);
num->array[0] = (sign == 0) ? 1 : 0;

- num_pos = g__numeric_bytes_per_prec[curcol->column_prec-1]-1;
+ num_pos = g__numeric_bytes_per_prec[curcol->column_prec]-1;
for (j = 0; j < colsize - 1; j++)
{
b_val = tds_get_byte(tds);
@@ -968,10 +969,11 @@
tds->state=TDS_DEAD;
}
}
+ return 0;
}

/*
-** tds_submit_query() sends a language string to the database server for
+ ** tds_submit_query() sends a language string to the database server for
** processing. TDS 4.2 is a plain text message with a packet type
of 0x01,
** TDS 7.0 is a unicode string with packet type 0x01, and TDS 5.0 uses a
** TDS_LANG_TOKEN to encapsulate the query and a packet type of 0x0f.
@@ -981,9 +983,9 @@
unsigned char *buf;
int bufsize;
TDS_INT bufsize2;
- int marker;
- int more_results;
- int cancelled;
+ // int marker;
+ // int more_results;
+ // int cancelled;


if (!query) return TDS_FAIL;
@@ -1033,7 +1035,7 @@
tds_put_n(tds, buf, bufsize);
tds_flush_packet(tds);

- free(buf);
+ FREE(buf);

return TDS_SUCCEED;
}
@@ -1088,8 +1090,8 @@
}
break;
}
- free(oldval);
- free(newval);
+ FREE(oldval);
+ FREE(newval);

return TDS_SUCCEED;
}
@@ -1143,8 +1145,8 @@
int len_msg;
int len_svr;
int len_sqlstate;
- int msg_type;
- char *tmpbuf;
+ // int msg_type;
+ // char *tmpbuf;


/* packet length */
@@ -1269,12 +1271,13 @@
tds->msg_info->line_number = 0;

if( tds->msg_info->message)
- free(tds->msg_info->message);
+ FREE(tds->msg_info->message);

if(tds->msg_info->server)
- free(tds->msg_info->server);
+ FREE(tds->msg_info->server);
if(tds->msg_info->proc_name)
- free(tds->msg_info->proc_name);
+ FREE(tds->msg_info->proc_name);
+ return 0;
}

/*
@@ -1285,6 +1288,7 @@
{
tds->out_flag=0x06;
tds_flush_packet(tds);
+ return 0;
}

/*
@@ -1305,6 +1309,7 @@
}
} while (!cancelled);
tds->state = TDS_COMPLETED;
+ return 0;
}
/* =========================== tds_is_result_row()
===========================
*
@@ -1422,7 +1427,7 @@
}

/*
-** tds_is_fixed_token()
+ ** tds_is_fixed_token()
** some tokens are fixed length while others are variable. This
function is
** used by tds_process_cancel() to determine how to read past a token
*/
@@ -1440,7 +1445,7 @@
}

/*
-** tds_get_token_size() returns the size of a fixed length token
+ ** tds_get_token_size() returns the size of a fixed length token
** used by tds_process_cancel() to determine how to read past a token
*/
int tds_get_token_size(int marker)
diff -bBdu tds.old/util.c tds.new/util.c
--- tds.old/util.c Thu Dec 21 17:20:51 2000
+++ tds.new/util.c Thu Dec 21 17:28:00 2000
@@ -105,8 +105,18 @@
num = ntohs(service->s_port);
}

- if (host==NULL || num==0)
+ if (host==NULL)
{
+ char addr [4];
+ int a0, a1, a2, a3;
+ sscanf (servername, "%d.%d.%d.%d", &a0, &a1, &a2, &a3);
+ addr [0] = a0;
+ addr [1] = a1;
+ addr [2] = a2;
+ addr [3] = a3;
+ host = gethostbyaddr (addr, 4, AF_INET);
+ }
+ if (!host || num==0){
ip[0] = '\0';
port[0] = '\0';
}
@@ -420,7 +430,7 @@
*
*
===========================================================================
*/
-static void tdsdump_dump_buf(
+void tdsdump_dump_buf(
const void *buf, /* (I) buffer
to dump */
int length) /* (I) number
of bytes in the buffer */
{

diff -bBdu tds.old/write.c tds.new/write.c
--- tds.old/write.c Thu Dec 21 17:21:00 2000
+++ tds.new/write.c Thu Dec 21 17:28:08 2000
@@ -42,7 +42,9 @@
for (i=0;i<n;i++)
tds_put_byte(tds,'\0');
}
+ return 0;
}
+
int tds_put_string(TDSSOCKET *tds, unsigned char *buf, int n)
{
return tds_put_buf(tds,buf,n,strlen(buf));
@@ -57,9 +60,11 @@
cpsize = ssize > dsize ? dsize : ssize;
memcpy(tempbuf,buf, cpsize);
tds_put_n(tds,tempbuf,dsize);
- free(tempbuf);
+ FREE(tempbuf);
tds_put_byte(tds,cpsize);
+ return 0;
}
+
int tds_put_int(TDSSOCKET *tds, TDS_INT i)
{
tds_put_n(tds,(unsigned char *)&i,sizeof(TDS_INT));
@@ -63,7 +68,9 @@
int tds_put_int(TDSSOCKET *tds, TDS_INT i)
{
tds_put_n(tds,(unsigned char *)&i,sizeof(TDS_INT));
+ return 0;
}
+
int tds_put_smallint(TDSSOCKET *tds, TDS_SMALLINT si)
{
tds_put_n(tds,(unsigned char *)&si,sizeof(TDS_SMALLINT));
@@ -67,7 +74,9 @@
int tds_put_smallint(TDSSOCKET *tds, TDS_SMALLINT si)
{
tds_put_n(tds,(unsigned char *)&si,sizeof(TDS_SMALLINT));
+ return 0;
}
+
int tds_put_tinyint(TDSSOCKET *tds, TDS_TINYINT ti)
{
tds_put_n(tds,(unsigned char *)&ti,sizeof(TDS_TINYINT));
@@ -71,7 +80,9 @@
int tds_put_tinyint(TDSSOCKET *tds, TDS_TINYINT ti)
{
tds_put_n(tds,(unsigned char *)&ti,sizeof(TDS_TINYINT));
+ return 0;
}
+
int tds_put_byte(TDSSOCKET *tds, unsigned char c)
{
if (tds->out_pos >= tds->env->block_size) {
@@ -79,13 +90,16 @@
tds_init_write_buf(tds);
}
tds->out_buf[tds->out_pos++]=c;
+ return 0;
}
+
int tds_put_bulk_data(TDSSOCKET *tds, unsigned char * buf, TDS_INT
bufsize)
{
-
tds->out_flag = 0x07;
tds_put_n(tds,buf,bufsize);
+ return 0;
}
+
int tds_init_write_buf(TDSSOCKET *tds)
{
memset(tds->out_buf,'\0',tds->env->block_size);
@@ -90,7 +104,9 @@
{
memset(tds->out_buf,'\0',tds->env->block_size);
tds->out_pos=8;
+ return 0;
}
+
int tds_write_packet(TDSSOCKET *tds,unsigned char final)
{
static int retval;
@@ -99,6 +115,8 @@
struct timeval selecttimeout;
time_t start, now;
int retcode = 0;
+ int sent,nbytes;
+ char *buffer;

tds->out_buf[0]=tds->out_flag;
tds->out_buf[1]=final;
@@ -137,7 +155,16 @@
}
}
/* Jeffs hack *** END OF NEW CODE */
- retval=write(tds->s,tds->out_buf,tds->out_pos);
+ buffer = tds->out_buf;
+ nbytes = tds->out_pos;
+ // retval=write(tds->s,tds->out_buf,tds->out_pos);
+ for (sent = 0; sent < nbytes;){
+ retval = write (tds->s, buffer + sent, nbytes - sent);
+ if (retval == -1){
+ break;
+ }
+ sent += retval;
+ }

if (signal(SIGPIPE, oldsig)==SIG_ERR) {
fprintf(stderr, "TDS: Warning: Couldn't reset SIGPIPE signal to
previous value\n");
@@ -161,4 +188,5 @@
tds_init_write_buf(tds);
}
/* GW added check for tds->s */
+ return 0;
}


--
Fabien Roy
Singleentry.com
107 RR 620 South, suite 117
Lakeway, TX 78734
Tel: (512) 266-6379 ext 1350
Fax: (512) 266-6375
Mob: (512) 796-9854
http://www.singleentry.com
Nisi fractum, noli refeci
Or
Aint Broke! Don't Fix It!
|\ _,,,---,,_ _,,---,,,_ /|
/,`.-'`' -. ;-;;,_ _,;;-; ._ `'`-.',\
|,4- ) )-,_. ,\ ( `'-' `-'' ) /, ._,-( ( -7,|
'---''(_/--' `-'\_) (_/`-' `--\_)``---`




  • Fix for: "The token datastream length was not correct. This is an internal protocol error.", Fabien Roy, 12/21/2000

Archive powered by MHonArc 2.6.24.

Top of Page