我用ODBC的sqlconnect连接MS SQL SERVER失败

demoxie1 2013-06-14 05:44:39
大家好,我用VS2008编写的C语言程序,在访问SQLSERVER数据的时候,sqlconnect()函数的返回值为-1。不知道什么原因。
我ODBC的数据源配置没有问题,测试是对的。下面是我的 程序,请帮忙指导下问题出在哪。谢谢。
我的ODBC数据源的配置是:用户DSN(系统DSN也试过,同样不行),数据源名称为LocalServer,描述为空,服务器为127.0.0.1(为本机,远程的也试过,不行),其他默认。
不知道问题在哪。
谢谢了。

// compile with: odbc32.lib
#include <stdio.h>
#include <windows.h>
#include <sqlext.h>
#include <sqltypes.h>
#include <odbcss.h>

void sqlConnect();

int main()
{
sqlConnect();
getchar();
return 0;
}

void sqlConnect()
{
SQLHENV henv;
SQLHDBC hdbc;
SQLHSTMT hstmt;
SQLRETURN retcode;
UCHAR sql1[79]="select * from tbl_saleinfo where saleinfo_ticketid = 101988902";
UCHAR szDSN[15] = "LocalServer";
UCHAR userID[6] = "sa";
UCHAR passWORD[10] = "123456";

/*UCHAR szDSN[15] = "HOST";
UCHAR userID[6] = "demo";
UCHAR passWORD[10] = "demo";*/


// Allocate environment handle
retcode=SQLAllocHandle(SQL_HANDLE_ENV,SQL_NULL_HANDLE,&henv);


if(retcode==SQL_SUCCESS || retcode==SQL_SUCCESS_WITH_INFO)
{
printf("i am here1.\n");
// Set the ODBC version environment attribute
retcode=SQLSetEnvAttr(henv,SQL_ATTR_ODBC_VERSION,(void*)SQL_OV_ODBC3,0);

if(retcode==SQL_SUCCESS || retcode==SQL_SUCCESS_WITH_INFO)
{
printf("i am here2.\n");
// Allocate connection handle 创建连接句柄,下面两个方法好像都可以
retcode=SQLAllocHandle(SQL_HANDLE_DBC,henv,&hdbc);
//retcode = SQLAllocConnect(henv,&hdbc);

if(retcode==SQL_SUCCESS || retcode==SQL_SUCCESS_WITH_INFO)
{
printf("i am here3.\n");
// Set login timeout to 5 seconds
SQLSetConnectAttr(hdbc, SQL_LOGIN_TIMEOUT, (SQLPOINTER)5, 0);

// Connect to data source
retcode=SQLConnect(hdbc, (SQLCHAR*)"LocalServer", SQL_NTS,(SQLCHAR*)"sa", SQL_NTS,(SQLCHAR*)"123456", SQL_NTS);

if((retcode==SQL_SUCCESS) || (retcode==SQL_SUCCESS_WITH_INFO))
{
printf("i am here4.\n");

retcode=SQLAllocHandle(SQL_HANDLE_STMT,hdbc,&hstmt);
if(retcode==SQL_SUCCESS || retcode==SQL_SUCCESS_WITH_INFO)
{

//绑定参数方式
char a[20]="Jim";
SQLINTEGER p=SQL_NTS;
char list[5];

printf("i am here5.\n");
//1.预编译
SQLPrepare(hstmt,sql1,79);//第三个参数与数组大小相同,而不是数据库列相同
//2.绑定参数值
SQLBindParameter(hstmt,1,SQL_PARAM_INPUT,SQL_C_CHAR,SQL_CHAR,200,0,&a,0,&p);
SQLExecute(hstmt);
printf("connection is OK\n");
//SQLExecDirect(hstmt,sql1,79);

SQLBindCol(hstmt,1,SQL_C_CHAR,list,5,0);
SQLFetch(hstmt);
printf("%s\n",list);
}
SQLDisconnect(hdbc);
}
else
printf("failed:\n");
SQLFreeHandle(SQL_HANDLE_DBC,hdbc);
}
}
}
}

我手上的分数不多了,抱歉。
...全文
1160 19 打赏 收藏 转发到动态 举报
写回复
用AI写文章
19 条回复
切换为时间正序
请发表友善的回复…
发表回复
demoxie1 2013-06-22
  • 打赏
  • 举报
回复
问题已经解决了,结贴。
赵4老师 2013-06-19
  • 打赏
  • 举报
回复
sprintf
demoxie1 2013-06-19
  • 打赏
  • 举报
回复
找到原因了,我的存储过程需要这样调用才行: retcode = SQLExecDirect (hstmt, (SQLCHAR *)"exec Linux_TicketInfo '1K1201MR1/', 'A011901', null, null, null, null", SQL_NTS); 不能用call的方式来调用。 接下来的问题是:如何用输入参数的方式来调用存储过程了。
demoxie1 2013-06-19
  • 打赏
  • 举报
回复
引用 14 楼 Cisco_zk 的回复:
你把odbc的connectstring设置成vfp的就行了。 具体的你可以用控件先生成,再研究一下就会懂的。
不会是connectstring的问题吧? 首先,SQLDriverConnect()的返回值没有问题。 其次,我用SQLExecDirect("select * from ...")是能正常工作的。 现在就是在调用存储过程的时候不行,不知道是我语言不对,还是什么别的原因。
demoxie1 2013-06-19
  • 打赏
  • 举报
回复
引用 17 楼 zhao4zhong1 的回复:
sprintf
谢谢。我已经解决了。 觉得用sprintf在ODBC SQL这不够专业。 我用了sqlbindparameter(),这样感觉专业些。呵呵。 retcode = SQLBindParameter(hstmt, 1, SQL_PARAM_INPUT, SQL_C_CHAR, SQL_CHAR, 20, 0, sTicketNO, 0, NULL); retcode = SQLBindParameter(hstmt, 2, SQL_PARAM_INPUT, SQL_C_CHAR, SQL_CHAR, 10, 0, sGateNO, 0, NULL); retcode = SQLExecDirect (hstmt, (SQLCHAR *)"exec Linux_TicketInfo ?, ?, null, null, null, null", SQL_NTS); 这样就OK了。
demoxie1 2013-06-18
  • 打赏
  • 举报
回复
问题找到了: SQLExecDirect()的第二个参数应该用: (SQLWCHAR *) "select saleinfo_ticketno from Tbl_SaleInfo where SaleInfo_TicketID = 100036921"而不是: (SQLWCHAR *) L"select saleinfo_ticketno from Tbl_SaleInfo where SaleInfo_TicketID = 100036921", 不能多这个L。 对C这块不熟,赵老师能解释一下吗? 谢谢。
Cisco_zk 2013-06-18
  • 打赏
  • 举报
回复
你把odbc的connectstring设置成vfp的就行了。 具体的你可以用控件先生成,再研究一下就会懂的。
demoxie1 2013-06-18
  • 打赏
  • 举报
回复
我现在在调用存储过程的时候,又碰到了问题: 运行SQLExecDirect()的时候返回-1。我的程序是这样的: int main() { RETCODE retcode; //不能加:Trusted_Connection=yes,不知道为什么 SQLCHAR ConnStr[255] = "DRIVER={SQL Server};SERVER=192.168.20.251;UID=demo;PWD=demo;DATABASE=SYYLW-XC;"; //SQLCHAR ConnStr[255] = "DIRVER={SQL Server};SERVER=127.0.0.1;UID=demo;PWD=demo;Trusted_Connection=yes;DATABASE=JHS;"; SQLWCHAR outConnStr[255]; SQLSMALLINT OutConnStrLen; //绑定参数方式 SQLINTEGER p=SQL_NTS; SQLCHAR sTicketNO[]="1K1201MR1/"; SQLCHAR sGateNO[]="A011901"; SQLWCHAR sTicketName[100]; SQLSMALLINT sTicketStatus = 0, sSoundNO=0; SQLINTEGER sTouristSum = 0; SQLLEN cbTicketNO = 10, cbTouristSum = 0, cbGateNO = 7, cbSoundNO=0, cbTicketStatus =0, cbTicketName = 0; //环境句柄 retcode = SQLAllocHandle(SQL_HANDLE_ENV, NULL, &henv); if (retcode == SQL_SUCCESS || retcode == SQL_SUCCESS_WITH_INFO) { retcode = SQLSetEnvAttr(henv, SQL_ATTR_ODBC_VERSION,(SQLPOINTER)SQL_OV_ODBC3, SQL_IS_INTEGER); } //连接句柄 if (retcode == SQL_SUCCESS || retcode == SQL_SUCCESS_WITH_INFO) { retcode = SQLAllocHandle(SQL_HANDLE_DBC, henv, &hdbc); //连接数据库 if (retcode == SQL_SUCCESS || retcode == SQL_SUCCESS_WITH_INFO) { retcode = SQLDriverConnect(hdbc, NULL, (SQLCHAR*)ConnStr, SQL_NTS, outConnStr, 255, &OutConnStrLen, SQL_DRIVER_NOPROMPT); //判断是否连接成功 if( retcode == SQL_SUCCESS || retcode == SQL_SUCCESS_WITH_INFO) { printf("连接成功\n"); retcode = SQLAllocHandle(SQL_HANDLE_STMT, hdbc, &hstmt); if(retcode == SQL_SUCCESS || retcode == SQL_SUCCESS_WITH_INFO) { // Bind the input parameter retcode = SQLBindParameter(hstmt, 1, SQL_PARAM_INPUT, SQL_C_CHAR, SQL_CHAR, 10, 0, sTicketNO, 0, NULL); if(retcode != SQL_SUCCESS && retcode != SQL_SUCCESS_WITH_INFO) return (1); retcode = SQLBindParameter(hstmt, 2, SQL_PARAM_INPUT, SQL_C_CHAR, SQL_CHAR, 7, 0, sGateNO, 0, NULL); if(retcode != SQL_SUCCESS && retcode != SQL_SUCCESS_WITH_INFO) return (1); retcode = SQLExecDirect (hstmt, (SQLCHAR *)"{call dbo.Linux_TicketInfo(?,?)}", SQL_NTS); if (retcode == SQL_SUCCESS || retcode == SQL_SUCCESS_WITH_INFO) { retcode = SQLBindCol(hstmt, 1, SQL_C_SSHORT, (SQLPOINTER)&sTicketStatus, 0, &cbTicketStatus); retcode = SQLBindCol(hstmt, 2, SQL_C_CHAR, sTicketName, 100, &cbTicketName); retcode = SQLBindCol(hstmt, 3, SQL_C_SSHORT, (SQLPOINTER)&sSoundNO, 0, &cbSoundNO); retcode = SQLBindCol(hstmt, 4, SQL_C_SLONG, (SQLPOINTER)&sTouristSum, 0, &cbTouristSum); retcode = SQLFetch(hstmt); if (retcode == SQL_ERROR || retcode == SQL_SUCCESS_WITH_INFO) printf("error.\n"); if (retcode == SQL_SUCCESS || retcode == SQL_SUCCESS_WITH_INFO) wprintf(L"TicketStatus:%d, TickeName: %S, SoundNO: %d, TouristSum: %d.\n",sTicketStatus, sTicketName, sSoundNO, sTouristSum); } SQLFreeHandle(SQL_HANDLE_STMT, hstmt); } SQLDisconnect(hdbc); } SQLFreeHandle(SQL_HANDLE_DBC,hdbc); } } SQLFreeHandle(SQL_HANDLE_ENV, henv); return 0; }
demoxie1 2013-06-17
  • 打赏
  • 举报
回复
谢谢,我都没积分了,不知道还能不能到其他地方提问。
demoxie1 2013-06-17
  • 打赏
  • 举报
回复
引用 10 楼 zhao4zhong1 的回复:
虚拟机和真机还是有细微差别的。
找到解决方法了。好像是我用VS2008创建项目的问题。我重新用VS2008 VC++创建了一个空项目,然后就可以了。我之前创建的是WIN32的项目。 不过又有了新的问题。 在执行SQLExecDirect()的时候,返回-1。部分代码如下: retcode = SQLDriverConnect(hdbc1, NULL, (SQLCHAR*)ConnStr, SQL_NTS, outConnStr, 255, &OutConnStrLen, SQL_DRIVER_NOPROMPT); //retcode = SQLDriverConnect(hdbc1, NULL, (SQLTCHAR*)ConnStr, SQL_NTS, NULL, NULL, NULL, SQL_DRIVER_NOPROMPT); //判断是否连接成功 if( retcode == SQL_SUCCESS || retcode == SQL_SUCCESS_WITH_INFO) { printf("连接成功\n"); retcode = SQLAllocHandle(SQL_HANDLE_STMT, hdbc1, &hstmt1); if(retcode == SQL_SUCCESS || retcode == SQL_SUCCESS_WITH_INFO) { retcode = SQLExecDirect(hstmt1, (SQLWCHAR *) L"select saleinfo_ticketno from Tbl_SaleInfo where SaleInfo_TicketID = 100036921", SQL_NTS); if (retcode == SQL_SUCCESS || retcode == SQL_SUCCESS_WITH_INFO) { retcode = SQLBindCol(hstmt1, 1, SQL_C_CHAR, sCustID, 100, &cbCustID); retcode = SQLFetch(hstmt1); if (retcode == SQL_SUCCESS || retcode == SQL_SUCCESS_WITH_INFO) wprintf(L"NO:%S\n",sCustID); else printf("error.\n"); } SQLFreeHandle(SQL_HANDLE_STMT, hstmt1); } SQLDisconnect(hdbc1); } SQLFreeHandle(SQL_HANDLE_DBC,hdbc1);
赵4老师 2013-06-17
  • 打赏
  • 举报
回复
虚拟机和真机还是有细微差别的。
demoxie1 2013-06-17
  • 打赏
  • 举报
回复
这样看,不是代码的问题,但不知道是什么问题。 我的是xp虚拟机 + vs2008,
demoxie1 2013-06-17
  • 打赏
  • 举报
回复
奇怪,我同事在window7上用vs2010开发的程序,放在我的机器上就不行。报-1.
demoxie1 2013-06-17
  • 打赏
  • 举报
回复
引用 5 楼 zhao4zhong1 的回复:
会用odbcad32.exe和cliconfg.exe吗? 安装MDAC了吗?
没用过,也没装MDAC。这些是什么工具? 我在配置ODBC数据源的时候,测试是没有问题的。但是C程序里面就是连不上。
赵4老师 2013-06-17
  • 打赏
  • 举报
回复
会用odbcad32.exe和cliconfg.exe吗? 安装MDAC了吗?
demoxie1 2013-06-17
  • 打赏
  • 举报
回复
引用 3 楼 zhao4zhong1 的回复:
现在查询分析器里面手动运行SQL语句无误后,再在代码中调试。
谢谢指导。 我现在连数据库都没能连上, 所以还谈不上调试SQL语句。 我在SQLConnect()或SQLDriverConnect()的时候就返回-1出错了。
赵4老师 2013-06-17
  • 打赏
  • 举报
回复
现在查询分析器里面手动运行SQL语句无误后,再在代码中调试。
快乐_石头 2013-06-14
  • 打赏
  • 举报
回复
如果数据源本身没有问题 程序问题建议到对应版块问 效率更高

69,371

社区成员

发帖
与我相关
我的任务
社区描述
C语言相关问题讨论
社区管理员
  • C语言
  • 花神庙码农
  • 架构师李肯
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧