|
| 1 | +[[prev](callpolicies.md)][[top](README.md)][[next](goodies.md)] |
| 2 | + |
| 3 | +#### Threads |
| 4 | + |
| 5 | +Warning: cpptcl *does not work* with the TCL thread package. |
| 6 | + |
| 7 | +#### Using threads |
| 8 | + |
| 9 | +You can use threads in TCL extensions. |
| 10 | +You can use threads with cpptcl. |
| 11 | +Be sure that you write good thread safe code. |
| 12 | +Be sure that all calls to TCL API's are properly protected with a mutex for exclusion. |
| 13 | +In general, cpptcl code itself has no thread specific safety code included. |
| 14 | + |
| 15 | +#### TCL's core use of threads |
| 16 | + |
| 17 | +The TCL interpreter is usually compiled with thread support by default on linux. |
| 18 | +TCL uses two threads. |
| 19 | +One thread is the main thread. |
| 20 | +The other thread is the notifier which wakes up the main thread from the select system call. |
| 21 | +Users can add more threads with the TCL threads package. |
| 22 | + |
| 23 | +##### TCL Thread package |
| 24 | + |
| 25 | +See https://www.tcl-lang.org/man/tcl/ThreadCmd/thread.htm for the documentation on the TCL thread package. |
| 26 | + |
| 27 | +The important point is that every TCL thread has a separate TCL interpreter. |
| 28 | +This interpreter is created in the TCL thread package with Tcl_CreateInterp C API. |
| 29 | +There is no API access to the interpreter pointer in the thread created by the TCL thread package. |
| 30 | +There is also no API to access the main Tcl_Interp *. |
| 31 | +But you created that interpreter, so one would have to save that pointer. |
| 32 | +cpptcl saves this interpreter pointer as the "default interpreter". |
| 33 | + |
| 34 | +#### cpptcl does not work with the TCL thread package |
| 35 | + |
| 36 | +##### cpptcl Interp wraps the Tcl_Interp * pointer |
| 37 | + |
| 38 | +cpptcl wraps the Tcl_Interp * pointer. |
| 39 | +One interpreter is cached in cpptcl to avoid having to pass it to every method. |
| 40 | +For example, the get method can be passed an interpreter, but a default value is provided. |
| 41 | +``` |
| 42 | +namespace Tcl { |
| 43 | +class object { |
| 44 | +... |
| 45 | +template <typename T> T get(interpreter &i = *interpreter::defaultInterpreter) const; |
| 46 | +
|
| 47 | +``` |
| 48 | +If you created the interpreters, then one can pass the specific interpreter as needed. |
| 49 | + |
| 50 | +Since TCL thread creates and hides the pointers to the interpreters, changes are required in TCL thread to fix this. |
| 51 | + |
| 52 | +The Tcl::interpreter::defaultInterpreter is a namescoped global. |
| 53 | + |
| 54 | +##### Mixing interpreter allocations will cause errors or worse |
| 55 | + |
| 56 | +You cannot mix allocation with free in TCL interpreters. |
| 57 | +Best case is that you get an error on Tcl_Free* on call ordering. |
| 58 | +Worse case is memory is corrupted. |
0 commit comments