Completing the documentation is one of the tasks we're trying to finish
up before releasing 4.5. Below is the complete man page for ns_ictl as
it currently stands. We'll be releasing a lot more information about
AOLserver 4.5 over then next few weeks as we finish things up and begin
testing internally here at AOL. Stay tuned! :-)
- n
ns_ictl
NAME <http://gin.office.aol.com:8000/html/ns_ictl.n.htm#NAME>
SYNOPSIS <http://gin.office.aol.com:8000/html/ns_ictl.n.htm#SYNOPSIS>
DESCRIPTION <http://gin.office.aol.com:8000/html/ns_ictl.n.htm#DESCRIPTION>
INTERPRETER ALLOCATION
<http://gin.office.aol.com:8000/html/ns_ictl.n.htm#INTERPRETER%20ALLOCATION>
INTERPRETER TRACES
<http://gin.office.aol.com:8000/html/ns_ictl.n.htm#INTERPRETER%20TRACES>
VIRTUAL SERVER TCL INITIALIZATION
<http://gin.office.aol.com:8000/html/ns_ictl.n.htm#VIRTUAL%20SERVER%20TCL%20INITIALIZATION>
EXAMPLES <http://gin.office.aol.com:8000/html/ns_ictl.n.htm#EXAMPLES>
SEE ALSO <http://gin.office.aol.com:8000/html/ns_ictl.n.htm#SEE%20ALSO>
KEYWORDS <http://gin.office.aol.com:8000/html/ns_ictl.n.htm#KEYWORDS>
------------------------------------------------------------------------
______________________________________________________________________________
NAME
ns_ictl − Facility to control AOLserver multi-threaded Tcl interpreters
SYNOPSIS
*ns_ictl addmodule* /module
/*ns_ictl cancel* /thread
/*ns_ictl cleanup
ns_ictl epoch
ns_ictl get
ns_ictl getmodules
ns_ictl gettraces* /which
/*ns_ictl once* /key script
/*ns_ictl oncleanup* /script
/*ns_ictl oncreate* /script
/*ns_ictl ondelete* /script
/*ns_ictl oninit* /script
/*ns_ictl package* /?-exact? package ?version?
/*ns_ictl runtraces* /which
/*ns_ictl save* /script
/*ns_ictl threads
ns_ictl trace* /when script
/*ns_ictl update
*
_________________________________________________________________
DESCRIPTION
This command provides access to the internal facilities to control and
configure multi-threaded Tcl interpreters in the context of AOLserver
virtual servers. It is normally used in startup initialization scripts
to define how new interpreters are initialized when created and to
support cleanup and re-initalization between transactions (e.g., HTTP
connections).
*ns_ictl addmodule* /module/
Add a module to the list of modules to be initialized at startup. This
command is not normally required as each module specified in the
AOLserver modules config section for the corresponding server (e.g.,
/ns/server/server1/modules/) is automatically added to the list.
*ns_ictl cancel* /thread/
Send an asynchronous interrupt request to the specified thread,
cancelling any script currently executing on any AOLserver created
interpreter (note the interrupt is not virtual-server specific). This
command utilizes the facilities of *Tcl_AsyncMark* to mark as ready a
callback registered with *Tcl_AsyncCreate*. The callback places an error
message in the interpreter result and returns *TCL_ERROR* to unwind the
call stack. The underlying Tcl facility has limitations, e.g., the
interrupt will only be noticed when Tcl checks via *Tcl_AsyncReady*
calls between commands and the interrupt can be caught with a *catch*
command. See the man page for *Tcl_AsyncCreate* for details.
*ns_ictl cleanup*
This command invokes any callbacks registered during a transaction via
the C-level *Ns_TclRegisterDefer* routine. Unlike callbacks registered
with the *ns_ictl trace deallocate* command or *Ns_TclRegisterTrace*
routine, these callbacks are executed only once and there is no
Tcl-level access to the underlying *Ns_TclRegisterDefer* routine.
*ns_ictl epoch*
This command returns the unique id for the current duplication script
for the virtual server. The id starts as 0 when the virtual server is
created and is incremented each time a new script is saved via the
*ns_ictl save* command.
*ns_ictl get*
Return the current duplication script for the virtual server. This
command is useful to view the duplication script created by the
initialization script at startup.
*ns_ictl getmodules*
Return the list of modules to be initialized at startup. This list
corresponds to the names of modules specified in the virtual server
modules config section, e.g., /ns/server/server1/modules/ unless
additional modules are added via the *ns_ictl addmodule* command.
*ns_ictl gettraces* /which/
Return the list of traces which will be invoked at the specified time.
The /which/ argument can be one of /create, delete, allocate,
deallocate, getconn/, or /freeconn/. The traces are returned in the
order in which they will be executed. Script level traces are returns as
strings to evaluate and C-level traces are returned with strings which
specify the address of the underlying C procedure and argument.
*ns_ictl once* /key script/
Evaluate given script once in the virtual server. The given key is a
string name which uniquely identifies the corresponding script. This
command is useful in a Tcl package which includes one-time
initialization routines, e.g., calls to *ns_register_proc* or
initialization of shared variables using *nsv_set* (see *EXAMPLES* below).
*ns_ictl oncleanup* /script/
This command is equivalent to *ns_ictl trace deallocate* /script/.
*ns_ictl oncreate* /script/
This command is equivalent to *ns_ictl trace create* /script/.
*ns_ictl ondelete* /script/
This command is equivalent to *ns_ictl trace delete* /script/.
*ns_ictl oninit* /script/
This command is equivalent to *ns_ictl trace allocate* /script/.
*ns_ictl package* /?-exact? package ?version?/
This command is used to require a package in the calling interpreter
and, if successfully loaded, in all other interpreters for the virtual
server. In addition to ensuring version consistency for the package, it
is equivalent to:
*set version [package require* /package ?version?/*]
ns_ictl trace allocate [list package require* /package/ *$version]*
*ns_ictl runtraces* /which/
This command runs the requested traces. The /which/ argument must be one
of *create*, *delete*, *allocate*, *deallocate*, *getconn*, or
*freeconn*. Direct calls to this command are not normally necessary as
the underlying C code will invoke the callbacks at the required times.
Exceptions include calling *ns_ictl runtraces* or testing purposes or to
mimic the normal cleanup and initialization work performed on between
transactions in a long running thread (see *EXAMPLES* below).
*ns_ictl save* /script/
Save the given script as the duplication script, incrementing the
virtual server epoch number. This command is normally called by the
bootstrap script after constructing the script to duplicate the
procedures defined by sourcing the various module initialization script
files.
*ns_ictl threads*
Return a list of all threads with interpreters for the virtual server.
The ids return are small strings which represent the underlying thread
ids and can be passed to the *ns_ictl cancel* command to send an
asynchronous cancel request.
*ns_ictl trace create* /script/
Register /script/ to be called when an interpreter is first created.
This is useful to create procedures, require packages, or initialize
other state to be used during the lifetime of the interpreter.
*ns_ictl trace delete* /script/
Register /script/ to be called before an interpreter is destroyed. This
is useful to free any resources which may have been allocated for the
interpreter during the lifetime of the interpreter.
*ns_ictl trace allocate* /script/
Register /script/ to be called each time an interpreter is allocated for
use by the *Ns_TclAllocateInterp* routine. This is useful for
reinitializing resources which may be used during a single transaction
in the interpreter.
*ns_ictl trace deallocate* /script/
Register /script/ to be called each time an interpreter is returned
after a transaction with the *Ns_TclDeAllocateInterp* routine. This is
useful for garbage collection, i.e., freeing any resources which may be
used during a single transaction in the interpreter.
*ns_ictl trace getconn* /script/
Register /script/ to be called each time an interpreter is returned and
associated with an HTTP connection with the *Ns_GetConnInterp* routine.
This could be useful to define variables relative to the HTTP request.
*ns_ictl trace freeconn* /script/
Register /script/ to be called each time an HTTP connection is closed.
This could be used to log information about the request, e.g., timing
statistics. Note that the interpreter may still be actively evaluating a
script after the connection is closed, i.e., this is not equivalent to
*ns_ictl trace deallocate* for connection-related interpreters.
*ns_ictl update*
This command can be used to atomically compare the epoch of the current
duplication script with the epoch of the interpreter, evaluating the
script and updating the epoch in the interpreter if they do not match.
This command is generally registered as a callback with *ns_ictl trace
allocate* by the legacy initialization code.
INTERPRETER ALLOCATION
Tcl interpreter in AOLserver are available on demand with state specific
to a virtual server. These interpreters are also expected to be reused
for multiple transactions (e.g., HTTP connections, scheduled procedures,
socket callbacks).
To support reuse, AOLserver provides the C-level *Ns_TclAllocateInterp*
routine to allocate an interpreter from a per-thread cache (creating and
initializing a new interpreter if necessary) and the
*Ns_TclDeAllocateInterp* routine to return an interpreter to the cache
when no longer required. All interpreters in the per-thread cache are
destroyed when a thread exists.
In general, only C-level extension writers need to call the C-level
API’s directly; the various Tcl-level interfaces in AOLserver (e.g.,
*ADP* pages, *ns_regiseter_proc*, *ns_schedule_proc*, *ns_thread*, etc.)
allocate and reuse interpreters using the C-level API’s automatically
before invoking the cooresponding script or ADP page.
INTERPRETER TRACES
To ensure a consistent state of interpreters when allocated and enable
cleanup and reinitialization between transactions, each virtual server
maintains a list of callbacks to be invoked at various points in the
lifetime of an interpreter. These callbacks are generally installed when
the server is initialized at startup and then called automatically by
the *Ns_TclAllocateInterp* and *Ns_TclDeAllocateInterp* API’s at the
appropriate times and in consistent order. The *Ns_TclRegisterTrace*
routine can be used to register C-level callbacks and the *ns_ictl
trace* command can be used to register Tcl script callbacks. The
*ns_ictl gettraces* command can be used to list all currently registered
callbacks, both at the Tcl script and C level.
Callbacks registered via the tracing facility are invoked in a specific
order depending on the type. Initialization style callbacks including
*create*, *allocate*, and *getconn* are invoked in FIFO order, with all
script callbacks invoked after all C-level callbacks. This enables
extension writers to utilize the facilities of previously initialized
extensions. Correspondingly, cleanup style callbacks including
*freeconn*, *deallocate*, and *delete* are invoked in LIFO order, with
all scripts callbacks invoked before C-level callbacks. This helps avoid
the possibility that a cleanup callback utilizes features of a
previously cleaned up extension.
In addition, the *ns_ictl package* command can be used to consistently
manage the loading of a Tcl package in all interpreters for a virtual
server. This feature is mostly a convenience routine built above the
generic trace framework with additional checks to ensure version number
consistency. Coupled with *ns_ictl once*, the *ns_ictl package* command
provides a clean framework to utilize Tcl packages in multi-threaded
AOLserver (see *EXAMPLES*).
VIRTUAL SERVER TCL INITIALIZATION
AOLserver also supports a Tcl initialization framework for virtual
servers based on callbacks registered by loadable modules and the
sourcing of scripts files located in corresponding directories. Options
to *ns_ictl* to support this framework include /save/, /get/, /epoch/,
and /update/ and are used in conjunction with the generic tracing
facility by the virtual server bootstrap script (normally
/bin/init.tcl/). The *ns_eval* command also relies on this framework to
support dynamic update of the state of interpreters.
This initialization framework pre-dates the Tcl package facilities and
utilizes introspection of the state of a startup interpreter at the end
of initialization to construct a single script which attempts to
duplicate the state in subsequent interpreters. Steps taken during this
initialization include:
1. Load all modules in the server’s module config section, e.g.,
/ns/server/server1/modules/. Modules with Tcl C-level extensions
typically call the legacy *Ns_TclInitInterps* routine or the more
general *Ns_TclRegisterTrace* routine with the /NS_TCL_TRACE_CREATE/
flag in their module init routine to register a callback to invoke when
new interpreters are created. The callback normally creates one or more
new commands in the interpreter with *Tcl_CreateObjCommand* but may
perform any per-interpreter initialization required, e.g., creating and
saving private state with the *Tcl_SetAssocData* facility. In addition,
as modules are loaded, the string name of the module is added to the
list of known modules.
2. After all C modules are loaded, AOLserver creates a new Tcl
interpreter for the virtual server, executing any trace callbacks
already registered via the loaded C modules (e.g., any
*Ns_TclInitInterps* callbacks) and then sources the virtual server
bootstrap script, normally /bin/init.tcl/. This script creates a few
utility procedures and then sources all /private/ and /public/ script
files in directories which correspond to loaded modules in the order in
which they were loaded. These directories are normally relative to the
virtual server and to the AOLserver installation directory, e.g.,
initialization script files for the module /mymod/ in the /server1/
virtual server would be searched for in the
/servers/server1/modules/tcl/mymod// and /modules/tcl/mymod//. Any
/init.tcl/ file found in each directory is sourced first with all
remaining files sourced in alphabetical order. In addition, any files in
the /public/ directory with identical names to files in the private
directory are skipped as a means to enable overloading of specific
functionality on a per-server basis. In practice, most modules only
contain shared utility procedures defined in the /public/ directories
and the /private/ directories are empty or non-existant. The script
files normally contain a mix of commands to evaluate once for server
configuration (e.g., a call to *ns_register_proc* to bind a Tcl
procedure to an HTTP request URL) with *proc* and *namespace* commands
to provide additional functionality in the interpreter.
3. After all script files have been sourced, the bootstrap script
code then uses a collection of recursive procedures to extract the
definitions of all procedures defined in all namespaces. The definitions
are used to construct a script which attempts to duplicate the state of
the initialization interpreters. This scripts is then saved as the
per-virtual server duplication script with the *ns_ictl save* command
which also increments the /epoch/ to 1. There are limits to this
approach to determine the full state, e.g., it does not attempt to
duplicate any global variables which may have been defined in the
startup scripts. Typically, startup scripts will use *nsv_set* or other
mechanisms to store such shared state.
4. The bootstrap code then uses the *ns_ictl trace allocate*
command to register a callback to the *ns_ictl update* command each time
an interpreter is allocated for use. In practice, interpreters are
created with the default /epoch/ of 0 and the first call to *ns_ictl
update* determines an out-of-date condition, evaluates the duplication
script, and increments the interpreter’s /epoch/ to 1 to match the state
created by the startup interp.
5. Subsequent calls the *ns_eval*, if any, will evaluate the
given script and then re-generate and save the duplication script as was
done at startup, incrementing the /epoch/ once again. In this way,
dynamic updates which are detected in other interpreters on their next
call to *ns_ictl update* can be supported in a limited fashion.
In practice, while generally successful, this duplication technique has
inhibited the clean use of proper Tcl package extensions and encouraged
the use of the *ns_eval* command which is generally not recommended for
the non-deterministic manner in which it attempts to dynamically
reconfigure a server. Also, commands required to configure the server
once (e.g., calls to *ns_register_proc*) are inter-mixed with *proc*
commands designed to extend functionality in all interpreters,
complicating configuration management.
As an alternative, the example below illustrates a means to more
explicitly manage configuration through a combination of direct calls to
*ns_ictl trace create* and *ns_ictl once*. Unfortunately, the all
encompassing nature of the legacy initialization approach makes it
difficult to incrementally move to this cleaner approach because the
duplication script construction code is unable to distinguish between
state created with the newer, cleaner *ns_ictl* commands and state
created as a side effect of one or more script files being sourced. As
such, it is expected the legacy initialization framework will remain in
place until AOLserver 5.x when it will be removed entirely in a
non-backwards compatible move towards the cleaner API’s.
EXAMPLES
This example illustrates the use of *ns_ictl package* and *ns_ictl once*
to load an AOLserver-aware Tcl package into a virtual server. The
following code could be added to the virtual server bootstrap script,
/bin/init.tcl/, to load /MyPkg/ in the virtual server:
#
# Startup code in bin/init.tcl:
#
# Load MyPkg in all interps (including this one).
#
ns_ictl package require MyPkg
This call will result in the package being loaded into the startup
interpreter in the ordinary Tcl fashion (see the *package* man page for
details). Ordinary Tcl extension packages would need no modifications
but packages which utilize AOLserver-specific features or require
garbage collection between transactions could also use *ns_ictl* for
finer grained control. For example, the /init.tcl/ script specified by
the *package ifneeded* command in the /MyPkg/ package’s /pkgIndex.tcl/
file could contains:
#
# Package code in lib/myPkg1.0/init.tcl:
#
#
package provide MyPkg 1.0
#
# Server init which will be executed the first time called,
# normally in the context of the startup interpreter as above.
#
ns_ictl once MyPkg {
# Register the run Tcl proc HTTP handler.
ns_register_proc /mypkg mkpkg::run
# Register a garbage collection callback.
ns_ictl trace deallocate mypkg::cleanup
}
#
# Code which will be invoked to initialize the package in
# all interpreters when required.
#
proc mypkg::run {} {
... handle /mypkg requests ...
}
proc mkpkg::cleanup {} {
... cleanup transaction resources for mypkg, e.g., db handles ...
}
SEE ALSO
Ns_TclAllocateInterp(3), Ns_TclDeAllocateInterp(3), Ns_GetConnInterp(3),
Ns_FreeConnInterp(3), Ns_TclInitInterps(3), Ns_TclRegisterTrace(3),
Ns_TclRegisterDeferred(3), ns_atclose(n), ns_eval(n).
KEYWORDS
threads, interpreters, traces, initialization
[EMAIL PROTECTED] wrote:
How can you know exactly what variables to clean up in each
namespace? Even the cleanup for the global namespace doesn't
completely wipe out all variables.
This is exactly the problem we ran into when thinking about how we
could better support Tcl namespace variables in AOLserver 4.5. The
short answer is that there doesn't necessarily seem to be a good way
to do this automatically for you, and instead it will be up to each
developer to delete the namespace variables they have created:
ns_ictl trace deallocate {... your cleanup here ...}
In AOLserver 4.5 the callbacks have been cleaned up and now fire in
the right order, lifo for cleanups, fifo for inits. Hope that helps!
I didn't know about this "trace" option for ns_ictl, it is not
documented:
http://www.panoptic.com/wiki/aolserver/Ns_ictl
is it equivalent to:
ns_ictl oncleanup script
Registers a script to be executed at Tcl interpreter cleanup time.
-john
--
AOLserver - http://www.aolserver.com/
To Remove yourself from this list, simply send an email to
<[EMAIL PROTECTED]> with the
body of "SIGNOFF AOLSERVER" in the email message. You can leave the
Subject: field of your email blank.
--
AOLserver - http://www.aolserver.com/
To Remove yourself from this list, simply send an email to <[EMAIL PROTECTED]>
with the
body of "SIGNOFF AOLSERVER" in the email message. You can leave the Subject:
field of your email blank.