• missing feature in TCL

    From aotto1968@21:1/5 to All on Sat Mar 25 10:41:24 2023
    Hi, I use a TCL project with multiple files involved and *proc* multiple times defined with the same name.
    the reason is to have a "generic" definition of a *proc* and sometimes I need a more specific definition
    who overwrites the generic definition.

    For debugging it would be very useful if I have something like `info proc-attribute *procname*`
    which return the *file* and/or the *line* where the *proc* was defined.

    The implementation is probably simple because this details are know at the time a *proc* defined.

    To make the interface more command it could look like:

    info proc args "procname" → return the arguments
    info proc body "procname" → return the body
    info proc file "procname" → return the definition file
    info proc line "procname" → return the definition line in file

    the proc-attribute feature could also be used to add additional features to a *proc* like *non-overwrite* etc

    mfg AO

    --- SoupGate-Win32 v1.05
    * Origin: fsxNet Usenet Gateway (21:1/5)
  • From Gerald Lester@21:1/5 to All on Sat Mar 25 09:27:06 2023
    On 3/25/23 04:41, aotto1968 wrote:

    Hi, I use a TCL project with multiple files involved and *proc* multiple times defined with the same name.
    the reason is to have a "generic" definition of a *proc* and sometimes I
    need a more specific definition
    who overwrites the generic definition.

    For debugging it would be very useful if I have something like `info proc-attribute *procname*`
    which return the *file* and/or the *line* where the *proc* was defined.

    The implementation is probably simple because this details are know at
    the time a *proc* defined.

    To make the interface more command it could look like:

    info proc args "procname"    → return the arguments
    info proc body "procname"    → return the body
    info proc file "procname"    → return the definition file
    info proc line "procname"    → return the definition line in file

    the proc-attribute feature could also be used to add additional features
    to a *proc* like *non-overwrite* etc

    mfg AO

    Please make a TIP of this and submit a proposed implementation.

    --- SoupGate-Win32 v1.05
    * Origin: fsxNet Usenet Gateway (21:1/5)
  • From et99@21:1/5 to All on Sat Mar 25 09:58:44 2023
    On 3/25/2023 2:41 AM, aotto1968 wrote:

    Hi, I use a TCL project with multiple files involved and *proc* multiple times defined with the same name.
    the reason is to have a "generic" definition of a *proc* and sometimes I need a more specific definition
    who overwrites the generic definition.

    For debugging it would be very useful if I have something like `info proc-attribute *procname*`
    which return the *file* and/or the *line* where the *proc* was defined.

    The implementation is probably simple because this details are know at the time a *proc* defined.

    To make the interface more command it could look like:

    info proc args "procname"    → return the arguments
    info proc body "procname"    → return the body
    info proc file "procname"    → return the definition file
    info proc line "procname"    → return the definition line in file

    the proc-attribute feature could also be used to add additional features to a *proc* like *non-overwrite* etc

    mfg AO

    I'm not certain, but you may be able to use [info
    frame] for this along with a [trace] and/or [rename]
    of [proc]. I've used info frame in a debugging tool to
    get line and file info. Also, an error has this info,
    but I don't know how it gets it.

    --- SoupGate-Win32 v1.05
    * Origin: fsxNet Usenet Gateway (21:1/5)
  • From Luc@21:1/5 to All on Sat Mar 25 16:02:09 2023
    On Sat, 25 Mar 2023 10:41:24 +0100, aotto1968 wrote:

    Hi, I use a TCL project with multiple files involved and *proc* multiple times defined with the same name. the reason is to have a "generic" definition of a *proc* and sometimes I need a more specific definition
    who overwrites the generic definition.

    For debugging it would be very useful if I have something like `info proc-attribute *procname*` which return the *file* and/or the *line*
    where the *proc* was defined.

    The implementation is probably simple because this details are know at
    the time a *proc* defined.

    To make the interface more command it could look like:

    info proc args "procname" → return the arguments
    info proc body "procname" → return the body
    info proc file "procname" → return the definition file
    info proc line "procname" → return the definition line in file

    the proc-attribute feature could also be used to add additional features
    to a *proc* like *non-overwrite* etc

    mfg AO


    I don't know. Seems to me that you should rather go with two procs:

    proc usual {args} {
    do the usual
    }

    proc chameleon {args} {
    some odd job
    }


    One has to wonder if you really need that much flexibility though. It's reasonable to guess that you probably deal with few enough situations
    that you could have one proc (or switch clause inside one proc) for each particular case instead of rewriting procs on the fly. Do you even remember what those temporary procs do when you maintain your code?
    And if you need to know *when* the proc was changed to use or manage it,
    it sounds like you are skating on thin ice.

    --
    Luc


    --- SoupGate-Win32 v1.05
    * Origin: fsxNet Usenet Gateway (21:1/5)
  • From aotto1968@21:1/5 to Luc on Sat Mar 25 20:54:03 2023
    On 25.03.23 20:02, Luc wrote:


    I don't know. Seems to me that you should rather go with two procs:

    proc usual {args} {
    do the usual
    }

    proc chameleon {args} {
    some odd job
    }


    One has to wonder if you really need that much flexibility though. It's reasonable to guess that you probably deal with few enough situations
    that you could have one proc (or switch clause inside one proc) for each particular case instead of rewriting procs on the fly. Do you even remember what those temporary procs do when you maintain your code?
    And if you need to know *when* the proc was changed to use or manage it,
    it sounds like you are skating on thin ice.


    Well, there is something like a "driver-proc" doing the controlling job and this "driver" is calling multiple "worker-proc(s)"
    to do the job. if I change the name of the "worker-proc" the "driver-proc" have to be updated as well → this is not good.

    mfg ao

    --- SoupGate-Win32 v1.05
    * Origin: fsxNet Usenet Gateway (21:1/5)
  • From briang@21:1/5 to All on Sat Mar 25 16:46:01 2023
    On Saturday, March 25, 2023 at 12:54:07 PM UTC-7, aotto1968 wrote:
    On 25.03.23 20:02, Luc wrote:


    I don't know. Seems to me that you should rather go with two procs:

    proc usual {args} {
    do the usual
    }

    proc chameleon {args} {
    some odd job
    }


    One has to wonder if you really need that much flexibility though. It's reasonable to guess that you probably deal with few enough situations
    that you could have one proc (or switch clause inside one proc) for each particular case instead of rewriting procs on the fly. Do you even remember
    what those temporary procs do when you maintain your code?
    And if you need to know *when* the proc was changed to use or manage it, it sounds like you are skating on thin ice.

    Well, there is something like a "driver-proc" doing the controlling job and this "driver" is calling multiple "worker-proc(s)"
    to do the job. if I change the name of the "worker-proc" the "driver-proc" have to be updated as well → this is not good.

    mfg ao

    When I write code that calls other procs that can be varied, I define the functions using variables, and the [apply] command to execute the functions. This way the proc(s) themselves can be passed to the "driver" by value. This still leaves you with
    the problem of identifying the source origin, but you do have more control over tracking where stuff came from. (See the [apply] command for details.)

    The "info proc" additions would still be a nice feature to have. Just know that there are cases where there isn't any identifiable file/line for a proc.

    -Brian

    --- SoupGate-Win32 v1.05
    * Origin: fsxNet Usenet Gateway (21:1/5)
  • From aotto1968@21:1/5 to briang on Sun Mar 26 08:37:30 2023
    On 26.03.23 00:46, briang wrote:
    On Saturday, March 25, 2023 at 12:54:07 PM UTC-7, aotto1968 wrote:
    On 25.03.23 20:02, Luc wrote:


    I don't know. Seems to me that you should rather go with two procs:

    proc usual {args} {
    do the usual
    }

    proc chameleon {args} {
    some odd job
    }


    One has to wonder if you really need that much flexibility though. It's
    reasonable to guess that you probably deal with few enough situations
    that you could have one proc (or switch clause inside one proc) for each >>> particular case instead of rewriting procs on the fly. Do you even remember >>> what those temporary procs do when you maintain your code?
    And if you need to know *when* the proc was changed to use or manage it, >>> it sounds like you are skating on thin ice.

    Well, there is something like a "driver-proc" doing the controlling job and this "driver" is calling multiple "worker-proc(s)"
    to do the job. if I change the name of the "worker-proc" the "driver-proc" have to be updated as well → this is not good.

    mfg ao

    When I write code that calls other procs that can be varied, I define the functions using variables, and the [apply] command to execute the functions. This way the proc(s) themselves can be passed to the "driver" by value. This still leaves you with
    the problem of identifying the source origin, but you do have more control over tracking where stuff came from. (See the [apply] command for details.)

    The "info proc" additions would still be a nice feature to have. Just know that there are cases where there isn't any identifiable file/line for a proc.

    -Brian

    I don't understand where is the advantage of overwrite and call a variable as lambda in difference of overwrite and call a proc.
    With a proc you have still the possible (as mentioned up) to get extra attributes like source,line etc

    -ao

    --- SoupGate-Win32 v1.05
    * Origin: fsxNet Usenet Gateway (21:1/5)
  • From Mole Cool@21:1/5 to All on Sun Mar 26 02:58:26 2023
    Hi, most of the stuff you require is available in the ‚info‘ command, the filename you can get on source. Of course only for a unique proc name.

    I really have no clue what you try to accomplish, but a namespace would not help here?

    --- SoupGate-Win32 v1.05
    * Origin: fsxNet Usenet Gateway (21:1/5)
  • From aotto1968@21:1/5 to Mole Cool on Sun Mar 26 12:13:13 2023
    On 26.03.23 11:58, Mole Cool wrote:
    Hi, most of the stuff you require is available in the ‚info‘ command, the filename you can get on source. Of course only for a unique proc name.

    I really have no clue what you try to accomplish, but a namespace would not help here?

    Hi,

    the file filename a *proc* is defined is *not* the same a filename when *proc* is used.
    the *info* command I get the the filename when *proc* is used,

    -ao

    --- SoupGate-Win32 v1.05
    * Origin: fsxNet Usenet Gateway (21:1/5)
  • From Mole Cool@21:1/5 to All on Sun Mar 26 03:26:19 2023
    But if you rename ‚source‘ you can have a pre and post command to see which procs a new and defined in the file, and the last one is the active one. Again, a renamed proc which will jump in the required namespace would for me the best. But you know
    the details 😉

    --- SoupGate-Win32 v1.05
    * Origin: fsxNet Usenet Gateway (21:1/5)
  • From Rich@21:1/5 to Mole Cool on Sun Mar 26 15:23:23 2023
    Mole Cool <[email protected]> wrote:
    I really have no clue what you try to accomplish, but a namespace
    would not help here?

    I am also quite confused as to what the OP is trying to accomplish.

    As best I understand from the vague descriptions given so far, it seems
    that the OP has an initial 'proc', say 'caller' which calls a second
    ('worker') to perform some task.

    I.e.:

    proc caller {arg1 arg2} {
    set result [worker $arg2]
    ...
    }

    And the OP wants to swap out different 'workers' for some reason such
    that which worker is actually called differs based on some condition.

    So they have something like this:

    proc swap_worker {arg} {
    switch -exact -- $arg {
    worker-1 {
    proc worker {arg} {
    ...
    }
    }
    worker-2 {
    proc worker {arg} {
    ... (different body from worker-1)
    }
    }
    }
    }

    And they call "swap_worker 0" and/or "swap_worker 1" as needed to
    "change the definition of 'worker'. Although I suspect from other
    vague descriptions by the op that my "proc worker" examples in the
    switch above are actually "source worker-1.tcl" and "source
    worker-2.tcl" instead.

    So, if this is what they are trying to do (and I don't know that it is,
    this is just what I've come up with by trying to "fill in the gaps"
    left by OP's vague description) then namespaces might be a solution
    to what they want that they have not tried yet.

    Namespaces allow creation of 'ensemble' commands. And each 'ensemble'
    itself has a "-map" which can optionally be setup to provide custom
    mapping of externally visible names to internal destination names
    within the ensemble.

    So the OP could setup a namespace with two (or more) 'worker'
    implementations inside. Then configure an ensemble to call one of the 'workers' (by appropriate -map setup). And later, when OP wants to
    swap "worker" implementation without changing callers, OP simply
    re-configures the -map for the ensemble to call the other worker inside
    the namespace ensemble.

    So OP's 'caller' would look like this:

    proc caller {arg1 arg2} {
    set result [my-project do-work $arg2]
    ...
    }

    Then, by adjustment of the -map configuration for the 'my-project'
    ensemble, the 'do-work' sub-command can call either of
    'my-project::worker-1' or 'my-project::worker-2' at different times.

    Achieving the same results as "replacing" 'worker' with a new 'worker'
    proc.

    And, the OP can simply introspect the -map to see which internal proc
    was being called at any given time. It is also possible that in the
    case of errors (which IIRC seemed to be OP's initial ask) that Tcl
    itself would report the actual used internal proc name for the
    destination of the ensemble. And if not, OP would just need to [catch]
    or [try] the call, then query the -map before outputting a custom error
    message to report "which proc was used at the time of the call".

    --- SoupGate-Win32 v1.05
    * Origin: fsxNet Usenet Gateway (21:1/5)