TCL与c/c++的互相调用

TCL与c/c++的互相调用
 
  TCL是一个解释型的语言,但是功能相当强大,一个重要原因就在于它的扩展性,现有的诸如http,socket,xml,oratcl等等,使得tcl可以轻松处理字符串、文件、通信以及数据库等等多方面的工作,甚至支持多线程。
  TCL的扩展可以通过调用tcl library来完成,具体的开发语言可能有多种,本文第一部分将以c/c++为例讨论。
  此外,缘于客户化的需要,也有可能在c/c++代码中调用tcl的咚咚,例如执行脚本啊,配置文件什么的,具体可见第二部分。
 
一.tcl中调用c/c++
  主要是利用c/c++处理复杂逻辑的能力,对于tcl来说,实际上就是一个扩展,因为你可以通过Tcl_CreateCommand函数,创建出一个新的tcl命令。
  具体操作方法需要分情况:
 
1.如果当前tcl版本支持load命令
语法:load libpackage.so
意义:在tcl中,当一个动态库libpackage.so被装载时,tcl会调用其中名为package_Init的函数,记住,名字一定不能错,包括大小写。这样,你就获得了一个入口,可以进入c/c++啦,你可以干任何事,当然,最重要的还是Tcl_CreateCommand了。
 
函数原型:Tcl_Command Tcl_CreateCommand(interp, cmdName, proc, clientData, deleteProc)
意义:创建一个新的tcl命令cmdName,对应的操作函数指针为proc。
 
这里以一个阶乘算法为例:目的是提供一个名为myfract的tcl命令,只接收一个参数,例如:
myfract 10
表示计算10的阶乘。
 
fract.c】:
#include "tcl.h"
int Tcl_myfract(ClientData notUsed, Tcl_Interp *interp, int argc, char **argv)
{
  int i, j;
  double res=1.0;
  char re[30];
  if (argc > 2)
  {
    Tcl_SetResult(interp, "wrong args: should be myfract", TCL_VOLATILE);
    return TCL_ERROR;
  }
  if (Tcl_GetInt(interp, argv[1], &i) != TCL_OK)
  {
    return TCL_ERROR;
  }
  for (j=1;j<=i;j++)
    res *= j;
  sprintf(re,"%le",res);
  Tcl_SetResult(interp, re, TCL_VOLATILE);
  return TCL_OK;
}
int Fract_Init(Tcl_Interp *Interp) {
  Tcl_CreateCommand (Interp, "myfract", (Tcl_CmdProc *)Tcl_myfract, (ClientData)0, 0);
  return TCL_OK;
}
 
Makefile】:
t = libfract.so
all: $t
clean:
  rm -f $t core
libfract.so: fract.c
  gcc -I. -shared -o $@ fract.c
 
test.tcl】: 
#!/usr/bin/tclsh
load ./libfract.so
set tcl_flag  [catch {myfract 2} return_str]
if {$tcl_flag != 0} {
  puts "OK:$return_str"
} else {
  puts "Error:$return_str"
}
 
运行:
linux:~/test/tcl # ./test.tcl
2.000000e+00
 
小结】:这里有两点需要注意,第一,Fract_Init是由TCL到c/c++的入口,而Tcl_CreateCommand则是由c/c++到TCL的入口;第二,编译动态库时不必链接tcl的开发库,因为这里仅仅需要引用。
     
还有swig可以使用
 
fract.i】:
%module fract
extern double myfract(int);

swig的语法这里就不详述了,具体可参见 www.swig.org
第一行表示模块名称叫做fract,对应前面的c/c++代码,就是说要创建的动态库叫做libfract.so;
第二行表示将要导出的函数,这个函数是需要你自己定义的。
 
fract.c】:
double myfract(int n)
{
  double res=1.0;
  int j;
  for (j=1;j<=n;j++)
  {
    res *= j;
  }
  return(res);
}
 
Makefile】:
t = fract_wrap.c libfract.so
all: $t
clean:
  rm -f $t core *.doc *.o
fract_wrap.c: fract.i
  swig -tcl fract.i
libfract.so:fract_wrap.c
  gcc -c fract.c fract_wrap.c
 
运行:
linux:~/test/tcl/swig # ./test.tcl
2.0
 
2.如果当前tcl版本不支持load命令
  我不知道哪个版本会这么原始,但即便如此,仍然有解决方法,那就是把扩展模块静态链接到执行文件中去,具体操作如下:
main.c】:
#include <tcl.h>
#include <stdio.h>
int Tcl_AppInit(Tcl_Interp *interp);
int main(int argc, char *argv[]) {
  Tcl_Main(argc, argv, Tcl_AppInit);
}
int Tcl_AppInit(Tcl_Interp *interp) {
  /* Initialize Tcl */
  if (Tcl_Init(interp) == TCL_ERROR) {
    return TCL_ERROR;
  }
  /* Initialize our extension */
  if (Fract_Init(interp) == TCL_ERROR) {
    return TCL_ERROR;
  }
  return TCL_OK;
}
 
Makefile】:
t = main
TCL_LIBS = -L/usr/lib -ltcl8.4
all: $t
clean:
  rm -f $t core
main:main.c fract.c
  gcc -I. ${TCL_LIBS} -o $@ main.c fract.c
 
运行:
linux:~/test/tcl # ./main
% myfract 8
4.032000e+04
% exit
linux:~/test/tcl # ldd main
        linux-gate.so.1 =>  (0xffffe000)
        libtcl8.4.so => /usr/lib/libtcl8.4.so (0x40030000)
        libc.so.6 => /lib/tls/libc.so.6 (0x400d8000)
        libdl.so.2 => /lib/libdl.so.2 (0x401f1000)
        libm.so.6 => /lib/tls/libm.so.6 (0x401f5000)
        /lib/ld-linux.so.2 (0x40000000)
       
我们发现,代码中重写了Tcl_AppInit函数,在tcl手册中该函数被形容为一个``hook'' procedure,很奇妙的东西。
因为最后会创建一个类似tclsh的执行文件,所以,tcl开发库必须链接上。
 
二.c/c++中调用tcl
  之所以会有这样的做法,主要是想利用tcl的客户化能力。
  例如把流程写在tcl脚本中,c/c++代码中仅仅执行Tcl_EvalFile就可以了,对于不同的服务,我们可以借助某种手段,绑定一个流程脚本,这样,当增加新的服务时或者服务流程需要变更时,不必修改源码,只要增加或修改配置文件/脚本文件即可,这也就实现了我们所说的客户化。

  我们只讨论几个常用的函数:
Tcl_CreateInterp    - 创建一个tcl解释器
Tcl_Eval            - 执行一个tcl命令
Tcl_VarEval         - 类似Tcl_Eval,只不过这个命令是被参数串起来的
Tcl_EvalFile        - 执行一个tcl脚本
Tcl_SetVar          - 设置tcl变量
Tcl_GetVar          - 获取tcl变量的值
 
下面是一个用法测试:
test.c】:
#include <tcl.h>
#include <string.h>
#include <stdlib.h>
#include <assert.h>
int main()
{
  Tcl_Interp* interp;
  char    *p;
  int tclres;
  //create interpreter
  interp = Tcl_CreateInterp();
  /*
   * Test Tcl_SetVar
   */
  char *varname = "SERVICE_NAME";
  char *varval = "MyServer";
  p = (char *)Tcl_SetVar(interp, varname, varval, TCL_GLOBAL_ONLY);
  assert ( p!=NULL && !strncmp(p, "MyServer", 8) );
  /*
   * Test Tcl_GetVar
   */
  p = (char *)Tcl_GetVar(interp, "SERVICE_NAME", TCL_GLOBAL_ONLY);
  assert ( p!=NULL && !strncmp(p, "MyServer", 8) );
  /*
   * Test Tcl_Eval
   */
  tclres = Tcl_eval_r(interp, "set CFG_val world");
  assert ( tclres == TCL_OK) ;
  p = (char *)Tcl_GetVar(interp, "CFG_val", TCL_GLOBAL_ONLY);
  assert ( p!=NULL && !strncmp(p, "world", 5) );
  /*
   * Test Tcl_VarEval
   */
  char *home = "./";
  tclres = Tcl_Vareval_r(interp, "source ", home, "test.cfg", NULL) ;
  assert ( tclres == TCL_OK) ;
  p = (char *)Tcl_GetVar(interp, "CFG_val", TCL_GLOBAL_ONLY);
  assert ( p!=NULL && !strncmp(p, "hello", 5) );
  /*
   * Test Tcl_EvalFile
   */
  char *path = "./test.cfg";
  tclres = Tcl_EvalFile(interp, path);
  assert ( tclres == TCL_OK) ;
  p = (char *)Tcl_GetVar(interp, "CFG_val", TCL_GLOBAL_ONLY);
  assert ( p!=NULL && !strncmp(p, "hello", 5) );
  //END
  printf("OK/n");
  }
 
Makefile】:
t = test
TCL_LIBS = -L/usr/lib -ltcl8.4
all: $t
clean:
  rm -f $t core
test: test.c
  gcc -I. ${TCL_LIBS} -o $@ test.c
linux:~/test/tcl/test # ./test
OK
 
三.后记
  在实践中,以上二者往往是联系在一起的,例如c/c++中调用的tcl脚本,也可以执行扩展命令(该命令完全可能是用c/c++代码实现的)。没有必要刻意去区分它们,正确的时候做正确的事,这就是原则。
 
  • 0
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
VIVADO经常使用TCL脚本对FPGA进行调试,通过JTAG转AXI对内部模块进行控制,但是TCL语言书籍比较少,这边是一个英文的TCL语言学习书籍. 第 1 章. TCL基本知识................................................................................................................1 1.1 什么是TCL..............................................................................................................................1 1.2 TCL自学工具...........................................................................................................................1 1.3 TCL软件包..............................................................................................................................2 1.4 TCL命令格式...........................................................................................................................2 1.5 TCL脚本文件和SOURCE 命令..................................................................................................3 1.6 可执行脚本文件(EXECUTABLE FILE)...........................................................................................3 1.7 获得帮助.................................................................................................................................4 1.7.1 Windows系统.............................................................................................................4 1.7.2 Unix系统......................................................................................................................4 第 2 章. 输出、赋值与替换........................................................................................................5 2.1 PUTS.........................................................................................................................................5 2.2 SET & UNSET..............................................................................................................................5 2.3 替换........................................................................................................................................6 2.3.1 $...................................................................................................................................6 2.3.2 []..................................................................................................................................6 2.3.3 " " 和{}..........................................................................................................................6 2.3.4 \...................................................................................................................................7 第 3 章. 数学表达式与EXPR命令..............................................................................................8 3.1 数学和逻辑运算符..................................................................................................................8 3.2 数学函数.................................................................................................................................8 3.3 数学运算举例.........................................................................................................................9 3.4 INCR命令................................................................................................................................9 第 4 章. 字符串........................................................................................................................10 4.1 基本命令集...........................................................................................................................10 4.2 APPEND命令..........................................................................................................................10 4.3 FORMAT命令..........................................................................................................................10 4.3.1 format命令说明......................................................................................................10 4.3.2 format举例..............................................................................................................11 4.4 SCAN命令.............................................................................................................................12 4.5 BINARY命令...........................................................................................................................13 4.6 SUBST命令..............................................................................................................................14 4.7 STRING 命令...........................................................................................................................15 4.7.1 string 命令列表.........................................................................................................15 4.7.2 字符串比较................................................................................................................16 4.7.3 string match字符串匹配.........................................................................................16 4.7.4 字符串替换................................................................................................................18 4.7.5 字符类别(class)测试.................................................................................................18 4.7.6 字符串映射................................................................................................................19 第 5 章. TCL列表操作..............................................................................................................20 5.1 列表命令集...........................................................................................................................20 5.2 LIST命令.................................................................................................................................20 5.3 CONCAT命令.........................................................................................................................21 5.4 LAPPEND命令........................................................................................................................21 5.5 LLENGTH 命令.........................................................................................................................22 5.6 LINDEX命令............................................................................................................................22 5.7 LRANGE命令..........................................................................................................................22 5.8 LINSERT 和LREPLACE命令........................................................................................................22 5.9 LSEARCH命令.........................................................................................................................23 5.10 LSORT命令.............................................................................................................................24 5.11 JOIN与SPLIT命令...................................................................................................................24 5.12 FOREACH控制结构................................................................................................................27 第 6 章. 数组............................................................................................................................28 6.1 数组的定义与格式................................................................................................................28 6.2 数组变量...............................................................................................................................29 6.3 多维数组...............................................................................................................................29 6.4 数组操作命令.......................................................................................................................30 6.4.1 array get命令.........................................................................................................30 6.4.2 array names命令....................................................................................................30 6.4.3 遍历数组...................................................................................................................31 6.4.4 用数组定义结构........................................................................................................31 第 7 章. 控制结构命令.............................................................................................................32 7.1 IF/ELSE命令............................................................................................................................32 7.2 FOR命令................................................................................................................................33 7.3 WHILE命令.............................................................................................................................33 7.4 BREAK 与 CONTINUE命令........................................................................................................34 7.5 SWITCH命令...........................................................................................................................34 7.6 CATCH 命令...........................................................................................................................35 7.7 ERROR命令............................................................................................................................36 7.8 RETURN 命令...........................................................................................................................37 7.9 EXIT命令................................................................................................................................37 第 8 章. 过程与作用域.............................................................................................................38 8.1 PROC—过程定义命令...........................................................................................................38 8.2 作用域...................................................................................................................................40 8.2.1 过程的作用域............................................................................................................40 8.2.2 变量的作用域............................................................................................................40 8.3 UPVAR命令............................................................................................................................42 8.4 RENAME命令.........................................................................................................................44 8.5 特殊变量...............................................................................................................................45 8.5.1 命令行参数................................................................................................................45 8.5.2 env--环境变量数组...................................................................................................45 8.6 EVAL命令..............................................................................................................................46 8.7 UPLEVEL命令..........................................................................................................................48 第 9 章. 正则表达式(REGULAR EXPRESSIONS)...................................................................49 9.1 REGEXP命令..........................................................................................................................49 9.2 REGSUB命令...........................................................................................................................51 9.3 正则表达式的语法................................................................................................................52 9.3.1 分支(branch)和原子(atom)....................................................................................52 9.3.2 基本语法...................................................................................................................52 9.3.2.1 匹配字符........................................................................................................................................52 9.3.2.2 限定匹配........................................................................................................................................53 9.3.2.3 方括号表达式与字符集.................................................................................................................53 9.3.2.4 匹配分支........................................................................................................................................54 9.3.2.5 量词(Qulifier)...........................................................................................................................54 9.3.2.6 子模式与匹配报告捕获.................................................................................................................55 9.3.2.7 反斜杠引用....................................................................................................................................56 9.3.2.8 匹配优先级....................................................................................................................................56 9.3.3 高级正则表达式(AREs).........................................................................................57 9.3.3.1 反斜杠换码(escape)序列............................................................................................................57 9.3.3.2 归整元素(collating element).....................................................................................................57 9.3.3.3 等价类(equivalence class)........................................................................................................58 9.3.3.4 字符类(character class).............................................................................................................58 9.3.3.5 非贪婪量词....................................................................................................................................59 9.3.3.6 约束量词........................................................................................................................................59 9.3.3.7 回退引用........................................................................................................................................59 9.3.3.8 前瞻(lookahead).........................................................................................................................60 9.3.3.9 换行符敏感的匹配.........................................................................................................................60 9.3.3.10 嵌入式选项...............................................................................................................................60 9.3.3.11 扩展语法...................................................................................................................................60 9.3.4 语法小结...................................................................................................................60 9.3.5 其它支持正则表达式的命令......................................................................................60 第 10 章. 名字空间.................................................................................................................62 10.1 创建名字空间...................................................................................................................62 10.2 用::限定符来使用变量和过程...........................................................................................62 10.3 名字空间的变量...............................................................................................................63 10.4 过程的进口与出口............................................................................................................64 10.5 内省(INTROSPECTION).........................................................................................................65 10.6 名字空间命令集...............................................................................................................65 第 11 章. 跟踪与调试.............................................................................................................67 11.1 CLOCK命令...........................................................................................................................67 11.1.1 clock clicks命令......................................................................................................67 11.1.2 clock seconds命令................................................................................................67 11.1.3 clock format命令...................................................................................................68 11.1.4 clock scan命令.......................................................................................................70 11.2 INFO 命令...............................................................................................................................71 11.2.1 info level..................................................................................................................72 11.2.2 info exists.................................................................................................................72 11.3 TRACE命令............................................................................................................................73 11.3.1 trace variable.........................................................................................................73 11.3.2 trace vdelete..........................................................................................................75 11.3.3 trace vinfo...............................................................................................................75 第 12 章. 脚本库与软件包......................................................................................................76 12.1 声明和使用软件包............................................................................................................76 12.1.1 软件包定位................................................................................................................76 12.1.2 声明软件包命令........................................................................................................76 12.1.3 加载软件包命令........................................................................................................76 12.1.4 自动加载与软件包索引.............................................................................................77 12.1.5 用链接库提供软件包.................................................................................................79 12.2 PACKAGE命令集...................................................................................................................80 12.3 小结..................................................................................................................................80 第 13 章. 文件操作与程序调用...............................................................................................81 13.1 文件操作...........................................................................................................................81 13.1.1 文件I/O....................................................................................................................81 13.1.2 文件系统信息命令.....................................................................................................82 13.1.2.1 glob命令.................................................................................................................................83 13.1.2.2 file命令集.................................................................................................................................83 13.2 程序调用...........................................................................................................................85 13.2.1 用open命令打开一个进程管道..............................................................................85 13.2.2 用exec命令调用程序..............................................................................................87 13.2.3 pid命令....................................................................................................................88 第 14 章. 套接字与事件驱动编程简介....................................................................................89 14.1 套接字编程.......................................................................................................................89 14.1.1 socket命令..............................................................................................................89 14.1.1.1 Client端socket命令..............................................................................................................89 14.1.1.2 Server端socket命令选项......................................................................................................90 14.1.2 用fconfigure配置套接字........................................................................................90 14.1.3 C/S编程举例............................................................................................................90 14.2 事件驱动编程...................................................................................................................93 14.2.1 after命令.................................................................................................................93 14.2.2 fileevent命令..........................................................................................................96 14.2.3 vwait命令................................................................................................................96 14.2.4 fconfigure命令.......................................................................................................97 14.2.4.1 fconfigure语法.......................................................................................................................97 14.2.4.2 非阻塞I/O................................................................................................................................98 14.2.4.3 缓冲..........................................................................................................................................98

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值