mainThe GNU Bourne-Again SHell - Support: sr #108991, Nested conditional command...

 
 

sr #108991: Nested conditional command evaluates outside function

Submitter:  Troy Etherton <troy>
Submitted:  Fri 04 Mar 2016 03:36:27 PM UTC
   
 
Category:  None Priority:  5 - Normal
Severity:  2 - Minor Status:  Invalid
Privacy:  Public Assigned to:  None
Open/Closed:  Open Operating System:  GNU/Linux
* Mandatory Fields

Add a New Comment Rich Markup
   

Thu 10 Mar 2016 01:32:00 AM UTC, comment #1: 

This is not a bug.  Let's break it down.

The && and || operators are left-associative.  That means that

[[ foo ]] && f1 || f2

is parsed as

{ [[ foo ]] && f1; } || f2

so the exit status of the first command (the stuff before the `||') determines whether or not f2 is executed.

When you pass "Function1" to the script as $1, the conditional command succeeds, and Function1 is executed.  The return status of Function1 is the return status of DEBUG, the last command executed in Function1's body.  The return status of DEBUG is false, because the status of the conditional command is false.  Since DEBUG returns failure, Function1 fails, the whole command to the left of the `||' fails, and Function2 is executed.

This is one of the ways c1 && c2 || c3 is not equivalent to an if statement.

Chet Ramey <chet>
Group administrator
Fri 04 Mar 2016 03:36:27 PM UTC, original submission:  

Not sure if this is a bug or my own misunderstanding of how conditional commands should work within BASH.

At the end of the script, I use a conditional command to choose between two functions using an OR statement.  If I include a conditional command (test for _DEBUG == on) inside of, and at the end of the first function (Function1), and that condition results in a FALSE, the second function after the OR in my original conditional command is executed.

If the nested conditional command is moved before another valid command, such as before the echo statement in Function1, the problem does not occur.  The nested conditional command seems to pass on its OR to the original conditional command.

Example script.  Pass 'Function1' as a param to see it fail.
# ==================== BEGIN SCRIPT ====================
#!/bin/bash
#_DEBUG=on

function DEBUG()
{
 [ "$_DEBUG" == "on" ] &&  echo -e "\e[1;34m$@\e[m"
}

Function1(){
  echo "Hello, I'm function one"
  DEBUG Leaving Function1
}

Function2(){
  echo "Hello, I'm function two"
}

[[ "$1" = "Function1" ]] && Function1 || Function2
# ====================== END SCRIPT ======================



Troy Etherton <troy>

 

(Note: upload size limit is set to 16384 kB, after insertion of the required escape characters.)

Attach Files:
   
   
Comment:
   

No files currently attached

 

Depends on the following items: None found

Items that depend on this one: None found

 

Carbon-Copy List
  • -email is unavailable- added by chet (Posted a comment)
  • -email is unavailable- added by troy (Submitted the item)
  • -email is unavailable- added by troy
  •  

    There are 0 votes so far. Votes easily highlight which items people would like to see resolved in priority, independently of the priority of the item set by tracker managers.

    Only logged-in users can vote.

     

    Follow 2 latest changes.

    Date Changed by Updated Field Previous Value => Replaced by
    2016-03-10 chet StatusNone Invalid
    2016-03-04 troy Carbon-Copy- Added -email is unavailable-

    Back to the top

    Powered by Savane 3.13-4448.
    Corresponding source code