]> git.pld-linux.org Git - packages/freetds.git/blob - freetds-cvs-fixes.patch
- release 3
[packages/freetds.git] / freetds-cvs-fixes.patch
1 diff -urN freetds/configure.ac freetds.current/configure.ac
2 --- freetds/configure.ac        2008-05-08 00:57:52.000000000 +0200
3 +++ freetds.current/configure.ac        2008-05-28 15:40:28.000000000 +0200
4 @@ -1,7 +1,7 @@
5  dnl Process this file with autoconf to produce a configure script.
6  
7  dnl ------------------------------------------------------------
8 -dnl $Id$
9 +dnl $Id$
10  dnl If you're trying to create a new configure test, try
11  dnl
12  dnl    http://autogen.sourceforge.net/conftest.html
13 @@ -240,7 +240,7 @@
14  ])
15  AC_CHECK_HEADERS([unistd.h errno.h wchar.h sys/time.h sys/types.h \
16  sys/param.h sys/stat.h sys/wait.h limits.h locale.h odbcss.h readpassphrase.h \
17 -signal.h libgen.h poll.h])
18 +signal.h libgen.h poll.h getopt.h])
19  if test $tds_mingw = no; then
20         AC_CHECK_HEADERS([sys/socket.h arpa/inet.h netdb.h netinet/in.h \
21  netinet/tcp.h paths.h sys/ioctl.h langinfo.h])
22 @@ -347,6 +347,16 @@
23  
24  TYPE_SOCKLEN_T
25  
26 +AC_MSG_CHECKING([whether getopt has optreset support])
27 +AC_TRY_LINK([#ifdef HAVE_GETOPT_H
28 +#include <getopt.h>
29 +#endif], [extern int optreset; optreset = 0;],
30 +[AC_MSG_RESULT(yes)
31 +AC_DEFINE(HAVE_GETOPT_OPTRESET, 1, [Define if your getopt(3) defines and uses optreset])],
32 +[AC_MSG_RESULT(no)]
33 +)
34 +
35 +
36  # ------------------------------------------------------------
37  # Checks for compiler characteristics.
38  # ------------------------------------------------------------
39 diff -urN freetds/include/cspublic.h freetds.current/include/cspublic.h
40 --- freetds/include/cspublic.h  2007-06-25 11:48:20.000000000 +0200
41 +++ freetds.current/include/cspublic.h  2008-05-19 16:23:52.000000000 +0200
42 @@ -34,7 +34,7 @@
43  #define TDS_STATIC_CAST(type, a) ((type)(a))
44  #endif
45  
46 -static const char rcsid_cspublic_h[] = "$Id$";
47 +static const char rcsid_cspublic_h[] = "$Id$";
48  static const void *const no_unused_cspublic_h_warn[] = { rcsid_cspublic_h, no_unused_cspublic_h_warn };
49  
50  #define CS_PUBLIC
51 @@ -447,6 +447,9 @@
52  
53  #define BLK_VERSION_100 CS_VERSION_100
54  #define BLK_VERSION_110 CS_VERSION_100
55 +#define BLK_VERSION_120 CS_VERSION_120
56 +#define BLK_VERSION_125 CS_VERSION_125
57 +#define BLK_VERSION_150 CS_VERSION_150
58  
59  #define CS_FORCE_EXIT  300
60  #define CS_FORCE_CLOSE  301
61 diff -urN freetds/include/tdsbytes.h freetds.current/include/tdsbytes.h
62 --- freetds/include/tdsbytes.h  2005-08-10 14:06:03.000000000 +0200
63 +++ freetds.current/include/tdsbytes.h  2008-05-26 14:49:56.000000000 +0200
64 @@ -20,7 +20,7 @@
65  #ifndef _tdsbytes_h_
66  #define _tdsbytes_h_
67  
68 -/* $Id$ */
69 +/* $Id$ */
70  
71  #ifndef _tds_h_
72  #error tds.h must be included before tdsbytes.h
73 @@ -61,9 +61,9 @@
74  #define TDS_GET_A2BE(ptr) TDS_GET_UA2BE(ptr)
75  
76  #define TDS_PUT_UA2LE(ptr,val) do {\
77 - ((TDS_UCHAR*)(ptr))[1] = (val)>>8; ((TDS_UCHAR*)(ptr))[0] = (val); } while(0)
78 + ((TDS_UCHAR*)(ptr))[1] = (TDS_UCHAR)((val)>>8); ((TDS_UCHAR*)(ptr))[0] = (TDS_UCHAR)(val); } while(0)
79  #define TDS_PUT_UA2BE(ptr,val) do {\
80 - ((TDS_UCHAR*)(ptr))[0] = (val)>>8; ((TDS_UCHAR*)(ptr))[1] = (val); } while(0)
81 + ((TDS_UCHAR*)(ptr))[0] = (TDS_UCHAR)((val)>>8); ((TDS_UCHAR*)(ptr))[1] = (TDS_UCHAR)(val); } while(0)
82  #define TDS_PUT_A2LE(ptr,val) TDS_PUT_UA2LE(ptr,val)
83  #define TDS_PUT_A2BE(ptr,val) TDS_PUT_UA2BE(ptr,val)
84  
85 @@ -78,11 +78,11 @@
86  #define TDS_GET_A4BE(ptr) TDS_GET_UA4BE(ptr)
87  
88  #define TDS_PUT_UA4LE(ptr,val) do {\
89 - ((TDS_UCHAR*)(ptr))[3] = (val)>>24; ((TDS_UCHAR*)(ptr))[2] = (val)>>16;\
90 - ((TDS_UCHAR*)(ptr))[1] = (val)>>8; ((TDS_UCHAR*)(ptr))[0] = (val); } while(0)
91 + ((TDS_UCHAR*)(ptr))[3] = (TDS_UCHAR)((val)>>24); ((TDS_UCHAR*)(ptr))[2] = (TDS_UCHAR)((val)>>16);\
92 + ((TDS_UCHAR*)(ptr))[1] = (TDS_UCHAR)((val)>>8); ((TDS_UCHAR*)(ptr))[0] = (TDS_UCHAR)(val); } while(0)
93  #define TDS_PUT_UA4BE(ptr,val) do {\
94 - ((TDS_UCHAR*)(ptr))[0] = (val)>>24; ((TDS_UCHAR*)(ptr))[1] = (val)>>16;\
95 - ((TDS_UCHAR*)(ptr))[2] = (val)>>8; ((TDS_UCHAR*)(ptr))[3] = (val); } while(0)
96 + ((TDS_UCHAR*)(ptr))[0] = (TDS_UCHAR)((val)>>24); ((TDS_UCHAR*)(ptr))[1] = (TDS_UCHAR)((val)>>16);\
97 + ((TDS_UCHAR*)(ptr))[2] = (TDS_UCHAR)((val)>>8); ((TDS_UCHAR*)(ptr))[3] = (TDS_UCHAR)(val); } while(0)
98  #define TDS_PUT_A4LE(ptr,val) TDS_PUT_UA4LE(ptr,val)
99  #define TDS_PUT_A4BE(ptr,val) TDS_PUT_UA4BE(ptr,val)
100  
101 diff -urN freetds/include/tds.h freetds.current/include/tds.h
102 --- freetds/include/tds.h       2007-12-27 14:45:22.000000000 +0100
103 +++ freetds.current/include/tds.h       2008-05-28 00:48:50.000000000 +0200
104 @@ -20,12 +20,16 @@
105  #ifndef _tds_h_
106  #define _tds_h_
107  
108 -/* $Id$ */
109 +/* $Id$ */
110  
111  #include <stdarg.h>
112  #include <stdio.h>
113  #include <time.h>
114  
115 +#if HAVE_ARPA_INET_H
116 +#include <arpa/inet.h>
117 +#endif /* HAVE_ARPA_INET_H */
118 +
119  /* forward declaration */
120  typedef struct tdsiconvinfo TDSICONV;
121  typedef struct tds_socket TDSSOCKET;
122 @@ -747,7 +751,7 @@
123  
124  
125  #define TDS_MAX_CAPABILITY     22
126 -#define MAXPRECISION           80
127 +#define MAXPRECISION           77
128  #define TDS_MAX_CONN           4096
129  #define TDS_MAX_DYNID_LEN      30
130  
131 diff -urN freetds/src/apps/freebcp.c freetds.current/src/apps/freebcp.c
132 --- freetds/src/apps/freebcp.c  2006-12-01 22:51:11.000000000 +0100
133 +++ freetds.current/src/apps/freebcp.c  2008-05-28 22:07:55.000000000 +0200
134 @@ -45,7 +45,7 @@
135  #include <sybdb.h>
136  #include "freebcp.h"
137  
138 -static char software_version[] = "$Id$";
139 +static char software_version[] = "$Id$";
140  static void *no_unused_var_warn[] = { software_version, no_unused_var_warn };
141  
142  void pusage(void);
143 @@ -351,6 +351,8 @@
144          */
145  
146         login = dblogin();
147 +       if (!login)
148 +               return FALSE;
149  
150         DBSETLUSER(login, pdata->user);
151         DBSETLPWD(login, pdata->pass);
152 @@ -372,8 +374,11 @@
153  
154         if ((*pdbproc = dbopen(login, pdata->server)) == NULL) {
155                 fprintf(stderr, "Can't connect to server \"%s\".\n", pdata->server);
156 +               dbloginfree(login);
157                 return (FALSE);
158         }
159 +       dbloginfree(login);
160 +       login = NULL;
161  
162         /* set hint if any */
163         if (pdata->hint) {
164 diff -urN freetds/src/apps/tsql.c freetds.current/src/apps/tsql.c
165 --- freetds/src/apps/tsql.c     2008-01-11 13:46:52.000000000 +0100
166 +++ freetds.current/src/apps/tsql.c     2008-05-31 10:53:39.000000000 +0200
167 @@ -85,7 +85,9 @@
168  #include "tdsconvert.h"
169  #include "replacements.h"
170  
171 -TDS_RCSID(var, "$Id$");
172 +TDS_RCSID(var, "$Id$");
173 +
174 +#define TDS_ISSPACE(c) isspace((unsigned char) (c))
175  
176  enum
177  {
178 @@ -301,6 +303,15 @@
179                 progname, progname);
180  }
181  
182 +static void
183 +reset_getopt(void)
184 +{
185 +#ifdef HAVE_GETOPT_OPTRESET
186 +       optreset = 1;
187 +#endif
188 +       optind = 1;
189 +}
190 +
191  /*
192   * The 'GO' command may be followed by options that apply to the batch.
193   * If they don't appear to be right, assume the letters "go" are part of the
194 @@ -324,7 +335,7 @@
195                 s = NULL;
196  
197         *opt_flags = 0;
198 -       optind = 0;             /* reset getopt */
199 +       reset_getopt();
200         opterr = 0;             /* suppress error messages */
201         while ((opt = getopt(argc, argv, "fhqtv")) != -1) {
202                 switch (opt) {
203 @@ -396,24 +407,24 @@
204                         opt_flags_str = optarg;
205                         break;
206                 case 'H':
207 -                       hostname = (char *) malloc(strlen(optarg) + 1);
208 -                       strcpy(hostname, optarg);
209 +                       free(hostname);
210 +                       hostname = strdup(optarg);
211                         break;
212                 case 'S':
213 -                       servername = (char *) malloc(strlen(optarg) + 1);
214 -                       strcpy(servername, optarg);
215 +                       free(servername);
216 +                       servername = strdup(optarg);
217                         break;
218                 case 'U':
219 -                       username = (char *) malloc(strlen(optarg) + 1);
220 -                       strcpy(username, optarg);
221 +                       free(username);
222 +                       username = strdup(optarg);
223                         break;
224                 case 'P':
225 -                       password = (char *) malloc(strlen(optarg) + 1);
226 -                       strcpy(password, optarg);
227 +                       free(password);
228 +                       password = strdup(optarg);
229                         break;
230                 case 'I':
231 -                       confile = (char *) malloc(strlen(optarg) + 1);
232 -                       strcpy(confile, optarg);
233 +                       free(confile);
234 +                       confile = strdup(optarg);
235                         break;
236                 case 'p':
237                         port = atoi(optarg);
238 @@ -524,6 +535,7 @@
239         }
240  
241         /* free up all the memory */
242 +       free(confile);
243         free(hostname);
244         free(username);
245         free(password);
246 @@ -572,6 +584,7 @@
247                 tsql_add_history(s);
248                 (*line)++;
249         }
250 +       fclose(fp);
251  }
252  
253  extern const char STD_DATETIME_FMT[];
254 @@ -709,7 +722,7 @@
255                  *  The rest of the line may include options that apply to the batch, 
256                  *  and perhaps whitespace.  
257                  */
258 -               if (0 == strncasecmp(s, "go", 2) && (strlen(s) == 2 || isspace(s[2]))) {
259 +               if (0 == strncasecmp(s, "go", 2) && (strlen(s) == 2 || TDS_ISSPACE(s[2]))) {
260                         char *go_line = strdup(s);
261                         assert(go_line);
262                         line = 0;
263 diff -urN freetds/src/dblib/bcp.c freetds.current/src/dblib/bcp.c
264 --- freetds/src/dblib/bcp.c     2008-01-08 16:38:31.000000000 +0100
265 +++ freetds.current/src/dblib/bcp.c     2008-05-26 14:49:56.000000000 +0200
266 @@ -71,7 +71,7 @@
267  }
268  TDS_PBCB;
269  
270 -TDS_RCSID(var, "$Id$");
271 +TDS_RCSID(var, "$Id$");
272  
273  #ifdef HAVE_FSEEKO
274  typedef off_t offset_type;
275 @@ -799,11 +799,13 @@
276  
277         if (dbproc->bcpinfo->direction == DB_QUERYOUT ) {
278                 if (tds_submit_query(tds, dbproc->bcpinfo->tablename) == TDS_FAIL) {
279 +                       fclose(hostfile);
280                         return FAIL;
281                 }
282         } else {
283                 /* TODO quote if needed */
284                 if (tds_submit_queryf(tds, "select * from %s", dbproc->bcpinfo->tablename) == TDS_FAIL) {
285 +                       fclose(hostfile);
286                         return FAIL;
287                 }
288         }
289 @@ -1061,6 +1063,7 @@
290                                         break;
291                                 }
292                                 if( plen != 0 && written != 1 ) {
293 +                                       fclose(hostfile);
294                                         dbperror(dbproc, SYBEBCWE, errno);
295                                         return FAIL;
296                                 }
297 @@ -1073,6 +1076,7 @@
298                                 if (buflen > 0) {
299                                         written = fwrite(hostcol->bcp_column_data->data, buflen, 1, hostfile);
300                                         if (written < 1) {
301 +                                               fclose(hostfile);
302                                                 dbperror(dbproc, SYBEBCWE, errno);
303                                                 return FAIL;
304                                         }
305 @@ -1082,6 +1086,7 @@
306                                 if (hostcol->terminator && hostcol->term_len > 0) {
307                                         written = fwrite(hostcol->terminator, hostcol->term_len, 1, hostfile);
308                                         if (written < 1) {
309 +                                               fclose(hostfile);
310                                                 dbperror(dbproc, SYBEBCWE, errno);
311                                                 return FAIL;
312                                         }
313 @@ -1094,6 +1099,7 @@
314                 dbperror(dbproc, SYBEBCUC, errno);
315                 return (FAIL);
316         }
317 +       hostfile = NULL;
318  
319         if (dbproc->hostfileinfo->firstrow > 0 && row_of_query < dbproc->hostfileinfo->firstrow) {
320                 /* 
321 @@ -1896,8 +1902,10 @@
322                 return FAIL;
323         }
324  
325 -       if (_bcp_start_copy_in(dbproc) == FAIL)
326 +       if (_bcp_start_copy_in(dbproc) == FAIL) {
327 +               fclose(hostfile);
328                 return FAIL;
329 +       }
330  
331         tds->out_flag = TDS_BULK;
332         tds_set_state(tds, TDS_QUERYING);
333 @@ -1922,6 +1930,7 @@
334  
335                         if (errfile == NULL && dbproc->hostfileinfo->errorfile) {
336                                 if (!(errfile = fopen(dbproc->hostfileinfo->errorfile, "w"))) {
337 +                                       fclose(hostfile);
338                                         dbperror(dbproc, SYBEBUOE, 0);
339                                         return FAIL;
340                                 }
341 @@ -2003,6 +2012,7 @@
342                                                 if (tds_process_simple_query(tds) != TDS_SUCCEED) {
343                                                         if (errfile)
344                                                                 fclose(errfile);
345 +                                                       fclose(hostfile);
346                                                         return FAIL;
347                                                 }
348                                                         
349 diff -urN freetds/src/dblib/dblib.c freetds.current/src/dblib/dblib.c
350 --- freetds/src/dblib/dblib.c   2008-01-02 00:09:46.000000000 +0100
351 +++ freetds.current/src/dblib/dblib.c   2008-05-26 14:49:56.000000000 +0200
352 @@ -76,7 +76,7 @@
353  #include <dmalloc.h>
354  #endif
355  
356 -TDS_RCSID(var, "$Id$");
357 +TDS_RCSID(var, "$Id$");
358  
359  static RETCODE _dbresults(DBPROCESS * dbproc);
360  static int _db_get_server_type(int bindtype);
361 @@ -3325,8 +3325,10 @@
362                         computeid = status;
363  
364                         for (i = 0;; ++i) {
365 -                               if (i >= tds->num_comp_info)
366 +                               if (i >= tds->num_comp_info) {
367 +                                       free(col_printlens);
368                                         return FAIL;
369 +                               }
370                                 resinfo = tds->comp_info[i];
371                                 if (resinfo->computeid == computeid)
372                                         break;
373 diff -urN freetds/src/odbc/odbc.c freetds.current/src/odbc/odbc.c
374 --- freetds/src/odbc/odbc.c     2008-04-30 16:59:32.000000000 +0200
375 +++ freetds.current/src/odbc/odbc.c     2008-06-18 06:11:39.000000000 +0200
376 @@ -60,7 +60,7 @@
377  #include <dmalloc.h>
378  #endif
379  
380 -TDS_RCSID(var, "$Id$");
381 +TDS_RCSID(var, "$Id$");
382  
383  static SQLRETURN _SQLAllocConnect(SQLHENV henv, SQLHDBC FAR * phdbc);
384  static SQLRETURN _SQLAllocEnv(SQLHENV FAR * phenv);
385 @@ -3608,10 +3608,6 @@
386                                         truncated = 1;
387                                         stmt->errs.lastrc = SQL_SUCCESS_WITH_INFO;
388                                 }
389 -                       } else {
390 -                               /* TODO change when we code cursors support... */
391 -                               /* stop looping, forward cursor support only one row */
392 -                               num_rows = 1;
393                         }
394                         if (drec_ard->sql_desc_octet_length_ptr)
395                                 *AT_ROW(drec_ard->sql_desc_octet_length_ptr, SQLLEN) = len;
396 @@ -3648,11 +3644,33 @@
397  SQLRETURN ODBC_API
398  SQLFetch(SQLHSTMT hstmt)
399  {
400 +       SQLRETURN ret;
401 +       SQLULEN  save_sql_desc_array_size;
402 +       SQLULEN *save_sql_desc_rows_processed_ptr;
403 +       SQLUSMALLINT *save_sql_desc_array_status_ptr;
404 +
405         INIT_HSTMT;
406  
407         tdsdump_log(TDS_DBG_FUNC, "SQLFetch(%p)\n", hstmt);
408  
409 -       ODBC_RETURN(stmt, _SQLFetch(stmt, SQL_FETCH_NEXT, 0));
410 +       if (stmt->dbc->env->attr.odbc_version != SQL_OV_ODBC3) {
411 +               save_sql_desc_array_size = stmt->ard->header.sql_desc_array_size;
412 +               stmt->ard->header.sql_desc_array_size = 1;
413 +               save_sql_desc_rows_processed_ptr = stmt->ird->header.sql_desc_rows_processed_ptr;
414 +               stmt->ird->header.sql_desc_rows_processed_ptr = NULL;
415 +               save_sql_desc_array_status_ptr = stmt->ird->header.sql_desc_array_status_ptr;
416 +               stmt->ird->header.sql_desc_array_status_ptr = NULL;
417 +       }
418 +
419 +       ret = _SQLFetch(stmt, SQL_FETCH_NEXT, 0);
420 +
421 +       if (stmt->dbc->env->attr.odbc_version != SQL_OV_ODBC3) {
422 +               stmt->ard->header.sql_desc_array_size = save_sql_desc_array_size;
423 +               stmt->ird->header.sql_desc_rows_processed_ptr = save_sql_desc_rows_processed_ptr;
424 +               stmt->ird->header.sql_desc_array_status_ptr = save_sql_desc_array_status_ptr;
425 +       }
426 +
427 +       ODBC_RETURN(stmt, ret);
428  }
429  
430  #if (ODBCVER >= 0x0300)
431 @@ -4564,6 +4582,8 @@
432         SQLLEN dummy_cb;
433         int nSybType;
434  
435 +       int extra_bytes = 0;
436 +
437         INIT_HSTMT;
438  
439         tdsdump_log(TDS_DBG_FUNC, "SQLGetData(%p, %u, %d, %p, %d, %p)\n", 
440 @@ -4601,42 +4621,140 @@
441         if (colinfo->column_cur_size < 0) {
442                 *pcbValue = SQL_NULL_DATA;
443         } else {
444 +               nSybType = tds_get_conversion_type(colinfo->column_type, colinfo->column_size);
445 +               if (fCType == SQL_C_DEFAULT)
446 +                       fCType = odbc_sql_to_c_type_default(stmt->ird->records[icol - 1].sql_desc_concise_type);
447 +               if (fCType == SQL_ARD_TYPE) {
448 +                       if (icol > stmt->ard->header.sql_desc_count) {
449 +                               odbc_errs_add(&stmt->errs, "07009", NULL);
450 +                               ODBC_RETURN(stmt, SQL_ERROR);
451 +                       }
452 +                       fCType = stmt->ard->records[icol - 1].sql_desc_concise_type;
453 +               }
454 +               assert(fCType);
455 +
456                 src = (TDS_CHAR *) colinfo->column_data;
457                 if (is_variable_type(colinfo->column_type)) {
458 -                       if (colinfo->column_text_sqlgetdatapos > 0
459 -                           && colinfo->column_text_sqlgetdatapos >= colinfo->column_cur_size)
460 -                               ODBC_RETURN(stmt, SQL_NO_DATA);
461 -
462 +                       int nread = 0;
463 +                       
464                         /* 2003-8-29 check for an old bug -- freddy77 */
465                         assert(colinfo->column_text_sqlgetdatapos >= 0);
466                         if (is_blob_type(colinfo->column_type))
467                                 src = ((TDSBLOB *) src)->textvalue;
468 -                       src += colinfo->column_text_sqlgetdatapos;
469 -                       srclen = colinfo->column_cur_size - colinfo->column_text_sqlgetdatapos;
470 +
471 +                       if (fCType == SQL_C_CHAR && colinfo->column_text_sqlgetdatapos) {
472 +                               TDS_CHAR buf[3];
473 +                               SQLLEN len;
474 +
475 +                               switch (nSybType) {
476 +                               case SYBLONGBINARY:
477 +                               case SYBBINARY:
478 +                               case SYBVARBINARY:
479 +                               case SYBIMAGE:
480 +                               case XSYBBINARY:
481 +                               case XSYBVARBINARY:
482 +                               case TDS_CONVERT_BINARY:
483 +                                       if (colinfo->column_text_sqlgetdatapos % 2) {
484 +                                               nread = (colinfo->column_text_sqlgetdatapos - 1) / 2;
485 +                                               if (nread >= colinfo->column_cur_size)
486 +                                                       ODBC_RETURN(stmt, SQL_NO_DATA);
487 +                                               
488 +                                               if (cbValueMax > 2) {
489 +                                                       len = convert_tds2sql(context, nSybType, src + nread, 1, fCType, buf, sizeof(buf), NULL);
490 +                                                       if (len < 2) {
491 +                                                               if (len < 0) 
492 +                                                                       odbc_convert_err_set(&stmt->errs, len);
493 +                                                               ODBC_RETURN(stmt, SQL_ERROR);
494 +                                                       }
495 +                                                       *(TDS_CHAR *) rgbValue = buf[1];
496 +                                                       *((TDS_CHAR *) rgbValue + 1) = 0;
497 +                                               
498 +                                                       rgbValue++;
499 +                                                       cbValueMax--;
500 +                                               
501 +                                                       extra_bytes = 1;
502 +                                                       nread++;
503 +
504 +                                                       if (nread >= colinfo->column_cur_size)
505 +                                                               ODBC_RETURN_(stmt);
506 +                                               } else {
507 +                                                       if (cbValueMax) 
508 +                                                               *(TDS_CHAR *) rgbValue = 0;
509 +                                                       odbc_errs_add(&stmt->errs, "01004", "String data, right truncated");
510 +                                                       ODBC_RETURN(stmt, SQL_SUCCESS_WITH_INFO);
511 +                                               }
512 +                                       } else {
513 +                                               nread = colinfo->column_text_sqlgetdatapos / 2;
514 +                                               if (nread >= colinfo->column_cur_size)
515 +                                                       ODBC_RETURN(stmt, SQL_NO_DATA);
516 +                                       }
517 +                                       
518 +                                       src += nread;
519 +                                       srclen = colinfo->column_cur_size - nread;
520 +                                       break;
521 +                               default:
522 +                                       if (colinfo->column_text_sqlgetdatapos >= colinfo->column_cur_size)
523 +                                               ODBC_RETURN(stmt, SQL_NO_DATA);
524 +                                               
525 +                                       src += colinfo->column_text_sqlgetdatapos;
526 +                                       srclen = colinfo->column_cur_size - colinfo->column_text_sqlgetdatapos;
527 +
528 +                               }
529 +                       } else if (fCType == SQL_C_BINARY) {
530 +                               switch (nSybType) {
531 +                               case SYBCHAR:
532 +                               case SYBVARCHAR:
533 +                               case SYBTEXT:
534 +                               case XSYBCHAR:
535 +                               case XSYBVARCHAR:
536 +                                       nread = (src[0] == '0' && toupper(src[1]) == 'X')? 2 : 0;
537 +                                               
538 +                                       while ((nread < colinfo->column_cur_size) && (src[nread] == ' ' || src[nread] == '\0')) 
539 +                                               nread++;
540 +
541 +                                       nread += colinfo->column_text_sqlgetdatapos * 2;
542 +                                       
543 +                                       if (nread && nread >= colinfo->column_cur_size)
544 +                                               ODBC_RETURN(stmt, SQL_NO_DATA);
545 +
546 +                                       src += nread;
547 +                                       srclen = colinfo->column_cur_size - nread;
548 +                                       break;
549 +                               default:
550 +                                       if (colinfo->column_text_sqlgetdatapos > 0
551 +                                       &&  colinfo->column_text_sqlgetdatapos >= colinfo->column_cur_size)
552 +                                               ODBC_RETURN(stmt, SQL_NO_DATA);
553 +                                               
554 +                                       src += colinfo->column_text_sqlgetdatapos;
555 +                                       srclen = colinfo->column_cur_size - colinfo->column_text_sqlgetdatapos;
556 +                               }
557 +                       } else {
558 +                               if (colinfo->column_text_sqlgetdatapos > 0
559 +                               &&  colinfo->column_text_sqlgetdatapos >= colinfo->column_cur_size)
560 +                                       ODBC_RETURN(stmt, SQL_NO_DATA);
561 +
562 +                               src += colinfo->column_text_sqlgetdatapos;
563 +                               srclen = colinfo->column_cur_size - colinfo->column_text_sqlgetdatapos;
564 +                       }
565                 } else {
566                         if (colinfo->column_text_sqlgetdatapos > 0
567 -                           && colinfo->column_text_sqlgetdatapos >= colinfo->column_cur_size)
568 +                       &&  colinfo->column_text_sqlgetdatapos >= colinfo->column_cur_size)
569                                 ODBC_RETURN(stmt, SQL_NO_DATA);
570  
571                         srclen = colinfo->column_cur_size;
572                 }
573 -               nSybType = tds_get_conversion_type(colinfo->column_type, colinfo->column_size);
574 -               if (fCType == SQL_C_DEFAULT)
575 -                       fCType = odbc_sql_to_c_type_default(stmt->ird->records[icol - 1].sql_desc_concise_type);
576 -               if (fCType == SQL_ARD_TYPE) {
577 -                       if (icol > stmt->ard->header.sql_desc_count) {
578 -                               odbc_errs_add(&stmt->errs, "07009", NULL);
579 -                               ODBC_RETURN(stmt, SQL_ERROR);
580 -                       }
581 -                       fCType = stmt->ard->records[icol - 1].sql_desc_concise_type;
582 -               }
583 -               assert(fCType);
584 +
585                 *pcbValue = convert_tds2sql(context, nSybType, src, srclen, fCType, (TDS_CHAR *) rgbValue, cbValueMax, NULL);
586                 if (*pcbValue < 0) {
587                         odbc_convert_err_set(&stmt->errs, *pcbValue);
588                         ODBC_RETURN(stmt, SQL_ERROR);
589                 }
590 -
591 +               
592 +               if (extra_bytes) {
593 +                       colinfo->column_text_sqlgetdatapos += extra_bytes;
594 +                       *pcbValue += extra_bytes;
595 +               }
596 +               
597                 if (is_variable_type(colinfo->column_type) && (fCType == SQL_C_CHAR || fCType == SQL_C_BINARY)) {
598                         /* calc how many bytes was readed */
599                         int readed = cbValueMax;
600 diff -urN freetds/src/odbc/unittests/cursor6.c freetds.current/src/odbc/unittests/cursor6.c
601 --- freetds/src/odbc/unittests/cursor6.c        1970-01-01 01:00:00.000000000 +0100
602 +++ freetds.current/src/odbc/unittests/cursor6.c        2008-06-06 18:52:23.000000000 +0200
603 @@ -0,0 +1,140 @@
604 +#include "common.h"
605 +
606 +/* Test SQLFetchScroll with no binded columns */
607 +
608 +static char software_version[] = "$Id$";
609 +static void *no_unused_var_warn[] = { software_version, no_unused_var_warn };
610 +
611 +static int bind_all = 0;
612 +static int normal_fetch = 0;
613 +static int use_cursors = 1;
614 +
615 +#define CHK(func,params) do { \
616 +       if (func params != SQL_SUCCESS) \
617 +               ODBC_REPORT_ERROR(#func); \
618 +       } while(0)
619 +
620 +static void Test(void)
621 +{
622 +#define ROWS 5
623 +       struct data_t {
624 +               SQLINTEGER i;
625 +               SQLLEN ind_i;
626 +               char c[20];
627 +               SQLLEN ind_c;
628 +       } data[ROWS];
629 +       SQLUSMALLINT statuses[ROWS];
630 +       SQLULEN num_row;
631 +
632 +       ResetStatement();
633 +
634 +       /* this should not fail or return warnings */
635 +       if (use_cursors) {
636 +               CHK(SQLSetStmtAttr, (Statement, SQL_ATTR_CONCURRENCY, int2ptr(SQL_CONCUR_READ_ONLY), 0));
637 +               CHK(SQLSetStmtAttr, (Statement, SQL_ATTR_CURSOR_TYPE, int2ptr(SQL_CURSOR_STATIC), 0));
638 +       }
639 +       CHK(SQLPrepare, (Statement, (SQLCHAR *) "SELECT c, i FROM #cursor6_test", SQL_NTS));
640 +       CHK(SQLExecute, (Statement));
641 +       CHK(SQLSetStmtAttr, (Statement, SQL_ATTR_ROW_BIND_TYPE, int2ptr(sizeof(data[0])), 0));
642 +       CHK(SQLSetStmtAttr, (Statement, SQL_ATTR_ROW_ARRAY_SIZE, int2ptr(ROWS), 0));
643 +       CHK(SQLSetStmtAttr, (Statement, SQL_ATTR_ROW_STATUS_PTR, statuses, 0));
644 +       CHK(SQLSetStmtAttr, (Statement, SQL_ATTR_ROWS_FETCHED_PTR, &num_row, 0));
645 +       if (bind_all)
646 +               CHK(SQLBindCol, (Statement, 1, SQL_C_CHAR, &data[0].c, sizeof(data[0].c), &data[0].ind_c));
647 +       CHK(SQLBindCol, (Statement, 2, SQL_C_LONG, &data[0].i, sizeof(data[0].i), &data[0].ind_i));
648 +
649 +#define FILL(s, n) do { \
650 +       int _n; for (_n = 0; _n < sizeof(s)/sizeof(s[0]); ++_n) s[_n] = n; \
651 +} while(0)
652 +       FILL(statuses, 9876);
653 +       num_row = -3;
654 +       data[0].i = 0xdeadbeef;
655 +       data[1].i = 0xdeadbeef;
656 +       if (normal_fetch)
657 +               CHK(SQLFetch, (Statement));
658 +       else
659 +               CHK(SQLFetchScroll, (Statement, SQL_FETCH_NEXT, 0));
660 +
661 +       /* now check row numbers */
662 +       printf("num_row %d statuses[0] %d statuses[1] %d odbc3 %d\n", (int) num_row,
663 +               (int) statuses[0], (int) statuses[1], use_odbc_version3);
664 +
665 +       if (use_odbc_version3 || !normal_fetch) {
666 +               if (num_row != ROWS || statuses[0] != SQL_ROW_SUCCESS || statuses[1] != SQL_ROW_SUCCESS) {
667 +                       fprintf(stderr, "result error 1\n");
668 +                       exit(1);
669 +               }
670 +       } else {
671 +               if (data[0].i != 1 || data[1].i != 0xdeadbeef) {
672 +                       fprintf(stderr, "result error 2\n");
673 +                       exit(1);
674 +               }
675 +       }
676 +
677 +       FILL(statuses, 8765);
678 +       num_row = -3;
679 +       if (normal_fetch)
680 +               CHK(SQLFetch, (Statement));
681 +       else
682 +               CHK(SQLFetchScroll, (Statement, SQL_FETCH_NEXT, 0));
683 +}
684 +
685 +static void Init(void)
686 +{
687 +       int i;
688 +       char sql[128];
689 +
690 +       Command(Statement, "CREATE TABLE #cursor6_test (i INT, c VARCHAR(20))");
691 +       for (i = 1; i <= 10; ++i) {
692 +               sprintf(sql, "INSERT INTO #cursor6_test(i,c) VALUES(%d, 'a%db%dc%d')", i, i, i, i);
693 +               Command(Statement, sql);
694 +       }
695 +
696 +}
697 +
698 +int
699 +main(int argc, char *argv[])
700 +{
701 +       unsigned char sqlstate[6];
702 +       unsigned char msg[256];
703 +       SQLRETURN retcode;
704 +
705 +       use_odbc_version3 = 1;
706 +       Connect();
707 +
708 +       retcode = SQLSetConnectAttr(Connection, SQL_ATTR_CURSOR_TYPE,  (SQLPOINTER) SQL_CURSOR_DYNAMIC, SQL_IS_INTEGER);
709 +       if (retcode != SQL_SUCCESS) {
710 +               CHK(SQLGetDiagRec, (SQL_HANDLE_DBC, Connection, 1, sqlstate, NULL, (SQLCHAR *) msg, sizeof(msg), NULL));
711 +               sqlstate[5] = 0;
712 +               if (strcmp((const char*) sqlstate, "S1092") == 0) {
713 +                       printf("Your connection seems to not support cursors, probably you are using wrong protocol version or Sybase\n");
714 +                       Disconnect();
715 +                       exit(0);
716 +               }
717 +               ODBC_REPORT_ERROR("SQLSetConnectAttr");
718 +       }
719 +
720 +       Init();
721 +
722 +#define ALL(n) for (n = 0; n < 2; ++n)
723 +       ALL(use_cursors)
724 +               ALL(bind_all)
725 +                       ALL(normal_fetch)
726 +                               Test();
727 +
728 +       Disconnect();
729 +
730 +       use_odbc_version3 = 0;
731 +
732 +       Connect();
733 +       Init();
734 +
735 +       ALL(use_cursors)
736 +               ALL(bind_all)
737 +                       ALL(normal_fetch)
738 +                               Test();
739 +
740 +       Disconnect();
741 +       
742 +       return 0;
743 +}
744 diff -urN freetds/src/odbc/unittests/getdata.c freetds.current/src/odbc/unittests/getdata.c
745 --- freetds/src/odbc/unittests/getdata.c        2008-01-29 11:14:31.000000000 +0100
746 +++ freetds.current/src/odbc/unittests/getdata.c        2008-06-18 06:11:39.000000000 +0200
747 @@ -1,6 +1,6 @@
748  #include "common.h"
749  
750 -static char software_version[] = "$Id$";
751 +static char software_version[] = "$Id$";
752  static void *no_unused_var_warn[] = { software_version, no_unused_var_warn };
753  
754  static char odbc_err[256];
755 @@ -11,7 +11,14 @@
756  {
757         memset(odbc_err, 0, sizeof(odbc_err));
758         memset(odbc_sqlstate, 0, sizeof(odbc_sqlstate));
759 -       if (!SQL_SUCCEEDED(SQLGetDiagRec(SQL_HANDLE_STMT, Statement, 1, (SQLCHAR *) odbc_sqlstate, NULL, (SQLCHAR *) odbc_err, sizeof(odbc_err), NULL))) {
760 +       if (!SQL_SUCCEEDED(SQLGetDiagRec(SQL_HANDLE_STMT
761 +                                       , Statement
762 +                                       , 1
763 +                                       , (SQLCHAR *) odbc_sqlstate
764 +                                       , NULL
765 +                                       , (SQLCHAR *) odbc_err
766 +                                       , sizeof(odbc_err)
767 +                                       , NULL))) {
768                 printf("SQLGetDiagRec should not fail\n");
769                 exit(1);
770         }
771 diff -urN freetds/src/odbc/unittests/Makefile.am freetds.current/src/odbc/unittests/Makefile.am
772 --- freetds/src/odbc/unittests/Makefile.am      2008-02-29 10:23:51.000000000 +0100
773 +++ freetds.current/src/odbc/unittests/Makefile.am      2008-06-06 18:52:23.000000000 +0200
774 @@ -1,4 +1,4 @@
775 -# $Id$
776 +# $Id$
777  TESTS          =       \
778                         t0001$(EXEEXT) t0002$(EXEEXT) t0003$(EXEEXT)\
779                         t0004$(EXEEXT) connect$(EXEEXT) print$(EXEEXT)\
780 @@ -21,7 +21,7 @@
781                         connect2$(EXEEXT) timeout4$(EXEEXT) freeclose$(EXEEXT) \
782                         cursor3$(EXEEXT) cursor4$(EXEEXT) cursor5$(EXEEXT) \
783                         attributes$(EXEEXT) hidden$(EXEEXT) blob1$(EXEEXT) \
784 -                       rowset$(EXEEXT)
785 +                       rowset$(EXEEXT) cursor6$(EXEEXT)
786  
787  check_PROGRAMS =       $(TESTS)
788  
789 @@ -81,6 +81,7 @@
790  hidden_SOURCES = hidden.c common.c common.h
791  blob1_SOURCES  = blob1.c common.c common.h
792  rowset_SOURCES = rowset.c common.c common.h
793 +cursor6_SOURCES        = cursor6.c common.c common.h
794  
795  AM_CPPFLAGS    =       -I$(top_srcdir)/include $(ODBC_INC) -DFREETDS_SRCDIR=\"$(srcdir)\"
796  if MINGW32
797 diff -urN freetds/src/server/server.c freetds.current/src/server/server.c
798 --- freetds/src/server/server.c 2008-01-07 15:07:21.000000000 +0100
799 +++ freetds.current/src/server/server.c 2008-05-28 23:08:03.000000000 +0200
800 @@ -30,7 +30,7 @@
801  #include "tds.h"
802  #include "tdssrv.h"
803  
804 -static char software_version[] = "$Id$";
805 +static char software_version[] = "$Id$";
806  static void *no_unused_var_warn[] = { software_version, no_unused_var_warn };
807  
808  void
809 @@ -117,13 +117,17 @@
810              const char *msgtext, const char *srvname, const char *procname, int line)
811  {
812         int msgsz;
813 +       size_t len;
814  
815         tds_put_byte(tds, TDS_INFO_TOKEN);
816 +       if (!procname)
817 +               procname = "";
818 +       len = strlen(procname);
819         msgsz = 4               /* msg no    */
820                 + 1             /* msg state */
821                 + 1             /* severity  */
822                 /* FIXME ucs2 */
823 -               + (IS_TDS7_PLUS(tds) ? 2 : 1) * (strlen(msgtext) + 1 + strlen(srvname) + 1 + strlen(procname))
824 +               + (IS_TDS7_PLUS(tds) ? 2 : 1) * (strlen(msgtext) + 1 + strlen(srvname) + 1 + len)
825                 + 1 + 2;        /* line number */
826         tds_put_smallint(tds, msgsz);
827         tds_put_int(tds, msgno);
828 @@ -135,10 +139,10 @@
829         tds_put_byte(tds, strlen(srvname));
830         /* FIXME ucs2 */
831         tds_put_string(tds, srvname, strlen(srvname));
832 -       if (procname && strlen(procname)) {
833 -               tds_put_byte(tds, strlen(procname));
834 +       if (len) {
835 +               tds_put_byte(tds, len);
836                 /* FIXME ucs2 */
837 -               tds_put_string(tds, procname, strlen(procname));
838 +               tds_put_string(tds, procname, len);
839         } else {
840                 tds_put_byte(tds, 0);
841         }
842 diff -urN freetds/src/tds/mem.c freetds.current/src/tds/mem.c
843 --- freetds/src/tds/mem.c       2007-12-31 11:06:50.000000000 +0100
844 +++ freetds.current/src/tds/mem.c       2008-05-26 14:49:56.000000000 +0200
845 @@ -47,7 +47,7 @@
846  #include <dmalloc.h>
847  #endif
848  
849 -TDS_RCSID(var, "$Id$");
850 +TDS_RCSID(var, "$Id$");
851  
852  static void tds_free_env(TDSSOCKET * tds);
853  static void tds_free_compute_results(TDSSOCKET * tds);
854 @@ -1040,6 +1040,9 @@
855  void
856  tds_free_connection(TDSCONNECTION * connection)
857  {
858 +       if (!connection)
859 +               return;
860 +
861         tds_dstr_free(&connection->server_name);
862         tds_dstr_free(&connection->client_host_name);
863         tds_dstr_free(&connection->server_host_name);
This page took 0.29398 seconds and 3 git commands to generate.