【tcl/tk]】tcl调用tuxedo的一个demo
Tuxedo是Oracle的一个商业中间件,一般用于通信。
如下是一个简单的调用tuxedo的so动态库实现,编译后,tcl脚本可以加载并调用这个so库实现对tuxedo的调用。
1. 代码例子,保存文件为tuxedotcl.cc
#include <stdio.h> #include <tcl.h> #include <stdlib.h> #include <unistd.h> #include <fcntl.h> #include <ctype.h> #include <string.h> #include <atmi.h> #include <userlog.h> #include <time.h> #include <sys/time.h> #include <stdarg.h> extern "C" { int Tuxedotcl_Init(Tcl_Interp *Interp); } void write_log(const char *fmt, ...) { va_list ap; int fd; char msg[4096]; va_start(ap, fmt); vsnprintf(msg, sizeof(msg), fmt, ap); va_end(ap); fd = open("tux_tcl.log", O_RDWR|O_APPEND|O_CREAT, 0666); if ( fd > 0 ) { write(fd, msg, strlen(msg)); close(fd); } } int Action_tpCall(int notUsed, Tcl_Interp *interp, int argc, char **argv) { char retBuffer[512]; long int sendlen,rcvlen; int retCall; char *sendbuf; char *rcvbuf; gettimeofday(&beginTime, NULL); memset(retBuffer, 0, sizeof(retBuffer)); if (argc != 4 && argc != 3) { Tcl_SetResult(interp, "Usage::Action_tpCall SERVERNAME sendBuffer WSNADDR", TCL_VOLATILE); return TCL_ERROR; } write_log("Action_tpCall:Begin"); if ( argv[3][0] != '\0' ) { tuxputenv(argv[3]); } //与服务端创建连接 if ((tpinit((TPINIT *)NULL)) == -1) { write_log("Action_tpCall::Error:Tpinit failed."); Tcl_SetResult(interp, "连接初始化失败", TCL_VOLATILE); return TCL_ERROR; } sendlen = strlen(argv[2]); //分配发送缓冲区 if((sendbuf = (char *) tpalloc("STRING", NULL, sendlen+1)) == NULL) { write_log("Action_tpCall::Error:allocating send buffer."); tpterm(); Tcl_SetResult(interp, "发送缓存失败", TCL_VOLATILE); return TCL_ERROR; } //分配接收缓冲区 if((rcvbuf = (char *) tpalloc("STRING", NULL, sendlen+1)) == NULL) { write_log("Action_tpCall::Error:allocating receive buffer."); tpfree(sendbuf); tpterm(); Tcl_SetResult(interp, "接收缓存失败", TCL_VOLATILE); return TCL_ERROR; } strcpy(sendbuf, argv[2]); //调用服务端发送请求方法,并接收返回信息,serverName为服务名 retCall = tpcall(argv[1], (char *)sendbuf, sendlen, (char **)&rcvbuf, &rcvlen, TPNOBLOCK); if( retCall == -1 ) { tpfree(sendbuf); tpfree(rcvbuf); sprintf(retBuffer, "TUXEDO服务:[%s]", argv[1]); Tcl_SetResult(interp, retBuffer, TCL_VOLATILE); return TCL_ERROR; } tpfree(sendbuf); tpterm(); Tcl_SetResult(interp, rcvbuf, TCL_VOLATILE); tpfree(rcvbuf); return TCL_OK; } int Tuxedotcl_Init(Tcl_Interp *Interp) { Tcl_CreateCommand (Interp, "Action_tpCall", (Tcl_CmdProc *)Action_tpCall, 0, 0); return TCL_OK; }
2. 编译
如果tuxedo安装在本地机器上时,可以简单的进行如下编译。
g++ -fPIC -shared -o libtuxedotcl.so tuxedotcl.cc -I$TUXDIR/include -ltcl -L${TUXDIR}/lib -ltux -lbuft -lfml -lfml32 -lengine -ldl -lpthread
如果tuxedo安装在远端机器上时,编译时需要链接网络相关的库文件 -lwsc -lgpnet
g++ -fPIC -shared -o libtuxedotcl.so tuxedotcl.cc -I$TUXDIR/include -ltcl -L${TUXDIR}/lib -lwsc -lbuft -lgpnet -lfml -lfml32 -lengine -ldl -lpthread
3. 执行
$ tclsh
% load libtuxedotcl.so
% Action_tpCall TOUPPER wangyfTestdddd
{0} WANGYFTESTDDDD
% Action_tpCall TOUPPER {This is a toupper test action}
{0} THIS IS A TOUPPER TEST ACTION
%