• Man of BASH!

    From Spectre@21:3/101 to Tenser on Monday, February 10, 2020 11:04:00
    Can you riddle me whats wrong with this?

    check () {
    if [ "$TEMP" == "v3.3:" ] || [ "$TEMP" == "" ]; then
    TEMP="firmware"
    sleep 5
    fi
    }

    Its not matching the v3.3: for some reason...

    Spec


    --- SuperBBS v1.17-3 (Eval)
    * Origin: < Scrawled in blood at The Lower Planes > (21:3/101)
  • From tenser@21:1/101 to Spectre on Monday, February 10, 2020 15:28:31
    On 10 Feb 2020 at 11:04a, Spectre pondered and said...

    Can you riddle me whats wrong with this?

    check () {
    if [ "$TEMP" == "v3.3:" ] || [ "$TEMP" == "" ]; then
    TEMP="firmware"
    sleep 5
    fi
    }

    Its not matching the v3.3: for some reason...

    How are you invoking it? Seems to work ok on my machine:

    ```
    : fat-dragon; cat check
    check() {
    if [ "$TEMP" == "v3.3:" ] || [ "$TEMP" == "" ]; then
    echo foo
    else
    echo bar
    fi
    }
    TEMP="v3.3:"
    check
    TEMP=""
    check
    TEMP="something"
    check
    : fat-dragon; bash check
    foo
    foo
    bar
    : fat-dragon; bash --version
    GNU bash, version 5.0.11(1)-release (x86_64-unknown-openbsd6.6)
    Copyright (C) 2019 Free Software Foundation, Inc.
    License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>

    This is free software; you are free to change and redistribute it.
    There is NO WARRANTY, to the extent permitted by law.
    : fat-dragon;
    ```

    First guess? `$TEMP` isn't set to what you think when `check`
    is invoked. Try adding `echo $TEMP` at the top of `check()`?

    --- Mystic BBS v1.12 A44 2020/02/04 (Windows/32)
    * Origin: Agency BBS | Dunedin, New Zealand | agency.bbs.nz (21:1/101)
  • From Spectre@21:3/101 to tenser on Monday, February 10, 2020 17:03:00
    Can you riddle me whats wrong with this?

    How are you invoking it? Seems to work ok on my machine:

    #!/bin/bash

    read () {
    TEMP="$(./temp | cut -d ' ' -f10)"
    TIME="$(date +%R)"
    }

    check () {
    if [ "$TEMP" == "v3.3:" ] || [ "$TEMP" == "" ]; then
    TEMP="firmware"
    sleep 5
    fi
    }


    TEMP="firmware"
    until [ $TEMP != "firmware" ]; do
    read
    echo $TIME $TEMP
    check
    done
    echo $TEMP $TIME
    echo "Frankston $TEMP at $TIME" > /bbs/ansi/local.tmp

    This is the rest of it, somehow v3.3: is making it into the output..

    Spec


    --- SuperBBS v1.17-3 (Eval)
    * Origin: < Scrawled in blood at The Lower Planes > (21:3/101)
  • From tenser@21:1/101 to Spectre on Tuesday, February 11, 2020 03:06:42
    On 10 Feb 2020 at 05:03p, Spectre pondered and said...

    Can you riddle me whats wrong with this?

    How are you invoking it? Seems to work ok on my machine:

    #!/bin/bash

    Ah, I see the issue. Let's break this apart.

    read () {
    TEMP="$(./temp | cut -d ' ' -f10)"
    TIME="$(date +%R)"
    }

    A metapoint: the shell has a builtin command called `read` to read
    a line from stdin and assign it to a shell variable. This definition
    shadows that builtin and makes it inaccessible. The upshot is that
    I would rename the function to something that doesn't mask the builtin:
    maybe `read_ver_and_time` or just `readvars`?

    check () {
    if [ "$TEMP" == "v3.3:" ] || [ "$TEMP" == "" ]; then
    TEMP="firmware"

    Note here that you _assign_ $TEMP to the string "firmware" if your
    conditions match. So if `$TEMP` was "v3.3:" it becomes "firmware".

    sleep 5
    fi
    }


    TEMP="firmware"
    until [ $TEMP != "firmware" ]; do

    This loop will not terminate while "$TEMP" == "firmware".

    Metanote: You're running an `until` loop on a negative
    equality check, which sorts of reads like a double-negative
    in English. Instead of ding that, consider just using a
    "while" loop:

    while [ $TEMP == "firmware" ]; do
    ...
    done

    read

    Here, you reassign $TEMP to whatever `read` found it to be...

    echo $TIME $TEMP
    check

    ...But here, you reassign $TEMP to "firmware", overwriting
    whatever $TEMP had been.

    done

    So when you go around the loop again, $TEMP is "firmware"
    and the loop never terminates.

    echo $TEMP $TIME
    echo "Frankston $TEMP at $TIME" > /bbs/ansi/local.tmp

    And these two lines are never executed. Note that the last
    line would truncate whatever had been in local.tmp, which
    may or may not be what you want.

    I'd probably split `read` and `check` up in a different way.
    This seems to work on my system:

    : fat-dragon; ls -A
    scr
    temp
    : fat-dragon; cat temp
    #!/bin/sh
    if [ -f .blarg ]; then
    echo ' v3.3:'
    fi
    touch .blarg
    : fat-dragon; cat scr
    #!/bin/sh

    version() {
    ./temp | cut -d ' ' -f 10
    }

    now() {
    date +%R
    }

    vers=$(version)
    while [ "$vers" != "v3.3:" ]; do
    sleep 5
    vers=$(version)
    done

    echo "Frankston $vers at $(now)"
    : fat-dragon; ./scr
    Frankston v3.3: at 14:05
    : fat-dragon; ls -A
    .blarg
    scr
    temp
    : fat-dragon; rm .blarg
    : fat-dragon;

    --- Mystic BBS v1.12 A44 2020/02/04 (Windows/32)
    * Origin: Agency BBS | Dunedin, New Zealand | agency.bbs.nz (21:1/101)
  • From Spectre@21:3/101 to tenser on Tuesday, February 11, 2020 12:09:00
    read () { TEMP="$(./temp | cut -d ' ' -f10)"

    the script ./temp queries the thermometer and returns a string full of garbage aside from the temp. Failures show up as "firmware", "", or "v3.3:"

    Ah, I see the issue. Let's break this apart.

    A metapoint: the shell has a builtin command called `read` to read a

    Ok so we rename read to something else... so far so good...

    check () { if [ "$TEMP" == "v3.3:" ] || [ "$TEMP" == "" ]; then TEMP="firmware"

    Note here that you _assign_ $TEMP to the string "firmware" if your conditions match. So if `$TEMP` was "v3.3:" it becomes "firmware".

    Whats happening here is... firmware, v3.3: and "" are all failures, but I'm looping on firmware, so if it equals one of the other two, I change it "firmware" A successful result looks like 21.5c. This logic mostly works, at least it does for "" and firmware, I don't comprende why v3.3: is an exception.

    TEMP="firmware" until [ $TEMP != "firmware" ]; do

    This loop will not terminate while "$TEMP" == "firmware".

    As noted above, its only checking one status on the loop, so other failures need to be made into a logical failure. It does terminate quite nicely in normal use. To be honest, when I started this, firmware was the only issue
    I was looking for, then I discovered the possible results.

    Metanote: You're running an `until` loop on a negative equality
    while [ $TEMP == "firmware" ]; do

    Again when I started what I had made sense, to me, and I was having trouble wrapping my head around the while possibility.. however it really amounts to the same thing... at least logically.. and yes yours makes more sense :)

    check

    ...But here, you reassign $TEMP to "firmware", overwriting
    whatever $TEMP had been.
    So when you go around the loop again, $TEMP is "firmware"
    and the loop never terminates.

    Thats partially right, there are 3 failures, but success is something that doesn't match any known failure, so while it can look endless, it does exit on anything other than those values.

    echo "Frankston $TEMP at $TIME" > /bbs/ansi/local.tmp

    And these two lines are never executed. Note that the last
    line would truncate whatever had been in local.tmp, which
    may or may not be what you want.

    So long as the values mentioned above aren't met this does get executed, the file local.tmp is only the current time, temperature so overwriting is a good thing. Its not a log as such. I have that being done elsewhere.

    I might have to cut it out, and pore over it a bit more in a shell, but I'm not
    entirely with your rewrite.. :/

    Spec


    --- SuperBBS v1.17-3 (Eval)
    * Origin: < Scrawled in blood at The Lower Planes > (21:3/101)
  • From tenser@21:1/101 to Spectre on Tuesday, February 11, 2020 15:51:26
    On 11 Feb 2020 at 12:09p, Spectre pondered and said...

    read () { TEMP="$(./temp | cut -d ' ' -f10)"

    the script ./temp queries the thermometer and returns a string full of garbage aside from the temp. Failures show up as "firmware", "", or "v3.3:"

    Oh. So that's meant to be _temperature_, not a generic name
    for a _temporary_ variable. Got it now.

    Note here that you _assign_ $TEMP to the string "firmware" if your conditions match. So if `$TEMP` was "v3.3:" it becomes "firmware".

    Whats happening here is... firmware, v3.3: and "" are all failures, but I'm looping on firmware, so if it equals one of the other two, I change
    it "firmware" A successful result looks like 21.5c. This logic mostly works, at least it does for "" and firmware, I don't comprende why v3.3: is an exception.

    Ah, so you want to loop while what the earlier script read is NOT
    a temperature. Ok, tracking.

    As noted above, its only checking one status on the loop, so other failures need to be made into a logical failure. It does terminate
    quite nicely in normal use. To be honest, when I started this, firmware was the only issue I was looking for, then I discovered the possible results.

    Another approach to take is to probe for a _successful_ result,
    and loop on anything else.

    Thats partially right, there are 3 failures, but success is something
    that doesn't match any known failure, so while it can look endless, it does exit on anything other than those values.

    I see. I'd rewrite it to terminate on successfully finding
    something that matches the temperature; the rest you simply
    loop.

    So long as the values mentioned above aren't met this does get executed, the file local.tmp is only the current time, temperature so overwriting
    is a good thing. Its not a log as such. I have that being done
    elsewhere.

    I might have to cut it out, and pore over it a bit more in a shell, but I'm not entirely with your rewrite.. :/

    Fair enough. Understanding the problem a little more, it
    sounds like you want to:

    1. Try and read the current temperature.
    2. If whatever you read doesn't look like a temperature, sleep
    for a bit and try again.
    3. Otherwise, echo the temperature read and the time to a file.

    The simplest way to do this is probably to pipe the cut output
    from your `temp` script through `grep` to match something that
    looks like a temperature. Here's my updated rewrite:

    : fat-dragon; rm .??*
    : fat-dragon; ls -A
    scr
    temp
    : fat-dragon; cat temp
    #!/bin/sh
    if ! [ -f .blarg ]; then
    echo ' v3.3:'
    touch .blarg
    elif ! [ -f .blat ]; then
    echo
    touch .blat
    elif ! [ -f .blah ]; then
    echo ' firmware'
    touch .blah
    else
    echo 25.2C
    fi
    : fat-dragon; cat scr
    #!/bin/sh

    temperature() {
    ./temp | cut -d ' ' -f 10 | egrep '^-?[0-9]+\.[0-9]+[Cc]$'
    }

    now() {
    date +%R
    }

    temp=$(temperature)
    while [ -z $temp ]; do
    sleep 5
    temp=$(temperature)
    done

    echo "Frankston $temp at $(now)"
    : fat-dragon; date; ./scr; date
    Tue Feb 11 02:46:27 UTC 2020
    Frankston 25.2C at 02:46
    Tue Feb 11 02:46:42 UTC 2020
    : fat-dragon; ls -A
    .blah
    .blarg
    .blat
    scr
    temp
    : fat-dragon; rm .??*
    : fat-dragon;

    Here, the magic is in the `egrep`: the point here is to
    use a (POSIX extended) regular expression to find something
    that "looks" like a temperature, and permit only those
    strings from the updated `temperature` function. If we
    see anything that doesn't look like a temperature, then
    the output from `temperature` will be empty, and we can
    test for that using the `-z` argument to `test` (`[` is
    another word for `test`). We'll loop as long as the
    temperature we read is empty; that is, until we get a
    useful value from the `temp` script.

    --- Mystic BBS v1.12 A44 2020/02/04 (Windows/32)
    * Origin: Agency BBS | Dunedin, New Zealand | agency.bbs.nz (21:1/101)
  • From Spectre@21:3/101 to tenser on Tuesday, February 11, 2020 16:49:00
    I'll take a closer look and see if I can't get this to work. On the flipside, I'm still wondering what is actually wrong with the check for "v3.3:" Considering it works for the other two values. I was wondering if the colon does something to it perhaps.. but I don't know...

    Thanks for your time,

    Spec


    *** THE READER V4.50 [freeware]
    --- SuperBBS v1.17-3 (Eval)
    * Origin: Scrawled in haste at The Lower Planes (21:3/101)
  • From Spectre@21:3/101 to Spectre on Tuesday, February 11, 2020 16:58:00
    Maybe I ought to borrow BP's hand and smack my forehead with it a few times. I just found the problem with the detection string... case.... it is in fact V3.3: that arrives not v3.3: gah..

    Spec


    --- SuperBBS v1.17-3 (Eval)
    * Origin: < Scrawled in blood at The Lower Planes > (21:3/101)
  • From Black Panther@21:1/186 to Spectre on Tuesday, February 11, 2020 07:46:24
    On 11 Feb 2020, Spectre said the following...

    Maybe I ought to borrow BP's hand and smack my forehead with it a few

    It doesn't help, but it makes you feel better for a moment. :)


    ---

    Black Panther(RCS)
    Castle Rock BBS

    --- Mystic BBS v1.12 A44 2020/02/04 (Linux/64)
    * Origin: Castle Rock BBS - bbs.castlerockbbs.com (21:1/186)