Skip to Content.
Sympa Menu

freetds - Re: [freetds] Set up client charset with DSN-less configuration

freetds AT lists.ibiblio.org

Subject: FreeTDS Development Group

List archive

Chronological Thread  
  • From: Johnny Yan <jyan AT tableau.com>
  • To: FreeTDS Development Group <freetds AT lists.ibiblio.org>
  • Subject: Re: [freetds] Set up client charset with DSN-less configuration
  • Date: Wed, 6 Jul 2016 17:28:29 +0000

Hi Frediano,

Thanks for the reply. Actually we use *W version of APIs internally. I think
the sample was over-simplified. Sorry about that.

Attached please find the updated sample with SQLDriverConnectW. However with
or without ClientCharset, we didn't see the client charset is set up
correspondingly.

Also about UTF-8, I think you implied this is your internal default? Is there
any way to change this?

If my understanding is correct, FreeTDS is doing something like <server
charset> <-> UCS-2LE <-> <client charset>. Let me know otherwise though. What
we want is to set the <client charset> to UTF-16 if possible.

Hope this doesn't make you more confused. But let me know if it does. We
could provide more info.

Thanks,
Johnny
________________________________________
From: FreeTDS <freetds-bounces AT lists.ibiblio.org> on behalf of Frediano
Ziglio <freddy77 AT gmail.com>
Sent: Wednesday, July 6, 2016 4:34:01 AM
To: FreeTDS Development Group
Subject: Re: [freetds] Set up client charset with DSN-less configuration

2016-07-05 22:16 GMT+01:00 Johnny Yan <jyan AT tableau.com>:
> Hi,
>
>
> We're writing data analytic application on Linux using FreeTDS(0.95.81)
> with unixODBC(2.3.4) to connect to SQL Server databases. Since we need to
> programmatically decide the hosts and other info provided by our customers,
> we decided to use the DSN-less configuration and pass the attributes
> through the connection string. However it seems that we can't set up the
> client side charset correctly.
>
>
> From the attached simple sample code, you could see that we could connect
> with that connection string(you need to change the server and
> username/password if you want to test it). And we get the following head in
> the freetds.log file,
>
>
> log.c:167:Starting log file for FreeTDS 0.95.81
> on 2016-06-30 18:17:32 with debug flags 0x4fff.
> iconv.c:328:tds_iconv_open(0xff47a0, UTF-8)
> iconv.c:187:local name for ISO-8859-1 is ISO-8859-1
> iconv.c:187:local name for UTF-8 is UTF-8
> iconv.c:187:local name for UCS-2LE is UCS-2LE
> iconv.c:187:local name for UCS-2BE is UCS-2BE
> iconv.c:346:setting up conversions for client charset "UTF-8"
> iconv.c:348:preparing iconv for "UTF-8" <-> "UCS-2LE" conversion
> iconv.c:395:preparing iconv for "ISO-8859-1" <-> "UCS-2LE" conversion
>
>
> It seems that the client charset is set to UTF-8. Am I correct? My
> understanding is that this is from the LANG env variable since we didn't
> specify it anywhere. Right?
>
>
> However when we try to specify the charset in the connection string, that
> is appending ";ClientCharset=UTF-16" to the connection string in the
> sample, we didn't observe the expected behavior. In another words, we still
> see the above bold line which implies that the ClientCharset attr in the
> connection string didn't make any difference. Is that expected? Did we do
> it correctly? Probably not. If so, how can we make it right?
>
>
> Let me know if you need any other info. Thank you very much!
>
>
> Johnny
>

Hi,
ClientCharset setting is for multi-byte, not wide. To use wide use
*W versions of the APIs. Internally utf-8 is used so this is normal.
ODBC does not force libTDS to do conversion to multi-byte so only one
conversion is done (beside metadatas).

Frediano
_______________________________________________
FreeTDS mailing list
FreeTDS AT lists.ibiblio.org
http://lists.ibiblio.org/mailman/listinfo/freetds

#include <stdio.h>
#include <sql.h>
#include <sqlext.h>
#include <string.h>

main() {
  SQLHENV env;
  SQLHDBC dbc;
  SQLRETURN ret;
  const char connstr[] = "DRIVER={FreeTDS};SERVER=mssql.test.tsi.lan;PORT=1433;UID=test;PWD=password;Fetch=2048;TDS_Version=auto;ClientCharset=UTF-16";
  SQLWCHAR instr[1024];
  int i = 0;
  for(; i < sizeof(connstr); i++)
  {
    instr[i] = (SQLWCHAR)connstr[i];
  }
  memset(instr+i, 0, sizeof(SQLWCHAR));
  SQLWCHAR outstr[1024];
  SQLSMALLINT outstrlen;

  SQLAllocHandle(SQL_HANDLE_ENV, SQL_NULL_HANDLE, &env);
  SQLSetEnvAttr(env, SQL_ATTR_ODBC_VERSION, (void *) SQL_OV_ODBC3, 0);
  SQLAllocHandle(SQL_HANDLE_DBC, env, &dbc);

  ret = SQLDriverConnectW(dbc, NULL, instr, SQL_NTS,
             outstr, sizeof(outstr), &outstrlen,
             SQL_DRIVER_COMPLETE);

  if (SQL_SUCCEEDED(ret)) {
    printf("Connected\n");
    printf("Returned connection string was:\n\t");
    for (int i = 0; i < outstrlen; i++)
    {
      printf("%c", outstr[i]);
    }
    printf("\n");
    SQLDisconnect(dbc);
  }

  SQLFreeHandle(SQL_HANDLE_DBC, dbc);
  SQLFreeHandle(SQL_HANDLE_ENV, env);
}



Archive powered by MHonArc 2.6.24.

Top of Page