Skip to Content.
Sympa Menu

freetds - Re: endian patch and Re: Strange server

freetds AT lists.ibiblio.org

Subject: FreeTDS Development Group

List archive

Chronological Thread  
  • From: "Michael Horowitz" <michael.horowitz AT storagenetworks.com>
  • To: freetds AT franklin.oit.unc.edu
  • Subject: Re: endian patch and Re: Strange server
  • Date: Tue, 22 Jan 2002 15:47:20 -0500


Hey Chris,

There was a thread about the big endian issue 2-3 weeks ago(I am
connecting from a Solaris box). I came across the same problem. I
initially just erased the second swap, but I was informed that would cause
problems when "emulate little endian" wasn't on. So, I conditioned the
second swap on "if (!tds->emul_little_endian)". I noticed you did "if
(tds->emul_little_endian)" in your patch, are you sure you didn't mean the
other way? tds_get_int does the swap if emul_little_endian is true, so
you only want to swap it if tds_get_int didn't swap it already, which is
if emul_little_endian is false.

In my experience with MS SQL Server 7.0, I MUST use emul_little_endian,
otherwise the datetime fields have their bytes backwards and the "swap
broken dates" seems to do nothing for me.

I tested this fix on MS SQL Server 7.0 and 2000 with mixed results.
This is what I wrote in a previous email about it:
"Actually, I tried SQL Server 2000 without "emulate-little-endian" and
with
that swap removed and the datetime fields are fine and so are the error
messages.
With SQL Server 7.0 with the same setup, the datetime fields are wrong,
and the error messages are messed up.

I tried using the following instead of completely removing the swap:
if (!tds->emul_little_endian) {
tds_swap_bytes(&rc, 4);
}
That fixed the error messages on SQL Server 7.0, but then they were
screwed up on SQL Server 2000."

Anyway, it seems that you have had a similar problem with the big endian
issue as me, so I wanted to chyme in with my experience with it. While
either of the fixes seems to work under specific configurations, I am not
sure what the final fix should be to make it work under all platforms and
with all types of SQL Servers both MS and Sybase.

Do you have any other info that might help with this?

Thanks,

Mike


> below is a patch that includes what I did for the
> strange serve on my network. More importantly however
> are the changes for big endian platforms towards the
> end with messages. The symptom I was seeing was that
> errors and messages were not being handled. trackign
> through the code this appeared to be happenning
> because of a double endian swap. I have also had to
> make some changes to the dblib call to the message
> handler as it did not pass the final argument of the
> line number. I will send that patch as it is rather
> simple if anyone needs it.
>
>
> *** freetds-0.53-orig/src/tds/token.c Sun Nov 25
> 19:04:17 2001
> --- freetds-0.53/src/tds/token.c Fri Jan 18
> 14:54:07 2002
> ***************
> *** 185,192 ****
> ack =
> tds_get_byte(tds);
> major_ver =
> tds_get_byte(tds);
> minor_ver =
> tds_get_byte(tds);
> ! tds_get_n(tds, NULL,
> len-4);
> ! tds_get_byte(tds);
> #ifdef WORDS_BIGENDIAN
> /*
> if (major_ver==7) {
> --- 185,219 ----
> ack =
> tds_get_byte(tds);
> major_ver =
> tds_get_byte(tds);
> minor_ver =
> tds_get_byte(tds);
> ! if ((major_ver == 4)
> && (minor_ver == 6)) {
> ! int tlen;
> ! char
> servname[1024];
> !
> ! tds_get_byte(tds);
> /* teeny version */
> ! tds_get_byte(tds);
> /* tiny version */
> ! tlen =
> tds_get_byte(tds); /* servname len */
> ! if (tlen >=
> sizeof(servname))
> ! tlen =
> sizeof(servname) - 1;
> ! tds_get_n(tds,
> servname, tlen);
> ! servname[tlen] =
> '\000';
> ! if
> (!strcmp(servname, "OpenServer")) {
> ! if (ack == 0)
> succeed=TDS_SUCCEED;
> ! }
> ! /* eat the rest of
> the data as below */
> ! tds_get_n(tds,
> NULL, len -
> !
> 1/*ack*/ -
> !
> 4/*major.minor.teeny.tiny*/ -
> !
> 1/*servnamelen*/ -
> !
> tlen/*servname*/);
> ! } else {
> ! /*
> ! * shouldn't these
> 2 just be len - 3?
> ! * after all we
> haev read 3 bytes of the
> ! * total length.
> ! */
> ! tds_get_n(tds,
> NULL, len-4);
> ! tds_get_byte(tds);
> ! }
> #ifdef WORDS_BIGENDIAN
> /*
> if (major_ver==7) {
> ***************
> *** 1134,1143 ****
>
> /* message number */
> /* swap bytes on bigendian systems
> (mlilback, 11/7/01) */
> rc = tds_get_int(tds);
> #ifdef WORDS_BIGENDIAN
> ! tds_swap_bytes(&rc, 4);
> ! #endif
> tds->msg_info->msg_number = rc;
>
> /* msg state */
> --- 1161,1176 ----
>
> /* message number */
> /* swap bytes on bigendian systems
> (mlilback, 11/7/01) */
> + /*
> + * we have to be careful not to double
> swap here.
> + * tds_get_int will swap out bytes for
> us if emul_little_endian
> + * is set. so lets not do it again
> (CRE, 01/18/01)
> + */
> rc = tds_get_int(tds);
> #ifdef WORDS_BIGENDIAN
> ! if (tds->emul_little_endian)
> ! tds_swap_bytes(&rc, 4);
> ! #endif /* WORDS_BIGENDIAN */
> tds->msg_info->msg_number = rc;
>
> /* msg state */
> ***************
> *** 1193,1199 ****
> --- 1226,1241 ----
> }
>
> /* line number in the sql statement where the
> problem occured */
> + /*
> + * we have to be careful not to double swap
> here.
> + * tds_get_int will swap out bytes for us if
> emul_little_endian
> + * is set. so lets do it again (CRE, 01/18/01)
> + */
> tds->msg_info->line_number =
> tds_get_smallint(tds);
> + #ifdef WORDS_BIGENDIAN
> + if (tds->emul_little_endian)
> +
> tds_swap_bytes(&tds->msg_info->line_number, 2);
> + #endif /* WORDS_BIGENDIAN */
>
> if (tds->msg_info->priv_msg_type) {
> rc = TDS_ERROR;
>
>
>
>
> __________________________________________________
> Do You Yahoo!?
> Send FREE video emails in Yahoo! Mail!
> http://promo.yahoo.com/videomail/




Archive powered by MHonArc 2.6.24.

Top of Page