Tuesday, January 08, 2013

Interface between C and TCL : Case I

C main program calls TCL interpreter to run an external TCL script. C and TCL communicate through variable values. TCL can call C function.

The C main program is listed below.

#include <stdio.h>
#include <tcl.h>

// a function to be called from within the TCL script
int my_func (ClientData data, Tcl_Interp *interp,
    int objc, Tcl_Obj *const objv[]);

int main(void) {

  Tcl_Interp *interp = NULL;

  interp = Tcl_CreateInterp();
  if (interp)
    printf("In C: TCL interpretor started.\n");

  Tcl_CreateObjCommand(interp, "my_cmd", my_func, 
      (ClientData)NULL, (Tcl_CmdDeleteProc *)NULL );

  printf("In C: TCL script begin.\n");
  if (Tcl_EvalFile(interp, "simple.tcl") == TCL_OK)
    printf("In C: TCL script end.\n");

  printf("C says: Hello, %s!\n", Tcl_GetVar(interp, "name", 0));

  Tcl_DeleteInterp(interp);
  if (Tcl_InterpDeleted(interp))
    printf("In C: TCL interpretor stopped.\n");

  return 0;

}


int my_func (ClientData data, Tcl_Interp *interp,
    int objc, Tcl_Obj *const objv[]) {
  int i;

  printf("In C: my_func() started.\n");
  printf("  obj[0] = %s.\n", Tcl_GetString(objv[0]));
  printf("  obj[1] = %s.\n", Tcl_GetString(objv[1]));
  if (Tcl_GetIntFromObj(interp, objv[2], &i) == TCL_OK)
    printf("  obj[2] = %d.\n", i);
  else
    printf("  obj[2] is not a integer!\n");
  printf("  obj[3] = %s.\n", Tcl_GetString(objv[3]));
  printf("In C: my_func() ended.\n");

  return TCL_OK;
}

The TCL script is listed below.

#!/usr/bin/tclsh

puts "Tcl calls: my_cmd (implemented as a C function)"
my_cmd abc +123 xyz

puts "----"

puts "Tcl asks: What is your name? "
gets stdin name

The program is compiled by (in Mac OS X 10.8.2) :

gcc -Wall -o main main.c -ltcl

The expected output is (in Mac OS X 10.8.2) :

$ ./main 
In C: TCL interpretor started.
In C: TCL script begin.
Tcl calls: my_cmd (implemented as a C function)
In C: my_func() started.
  obj[0] = my_cmd.
  obj[1] = abc.
  obj[2] = 123.
  obj[3] = xyz.
In C: my_func() ended.
----
Tcl asks: What is your name? 
Brittle
In C: TCL script end.
C says: Hello, Brittle!
In C: TCL interpretor stopped.

No comments: