1

I have a problem with a simple bash script..

#!/bin/bash
libc_main_ver=$(dpkg -l |grep libc6 |awk '{print$3}' |awk -F .
'{print$1}'|xargs -n 1)
if [ "$libc_main_ver" -eq 2 ] ;then
echo ok
else 
echo nope
fi
exit  0

When i try execute the script it gives me the error:

2: integer expression expected

What's the problem?

dpkg -l |grep libc6 |awk '{print$3}' |awk -F . '{print$1}'|xargs -n 1

This prints only 2 not other values.

Some suggestions?

3
  • What does dpkg -l | grep libc6 output? Commented Feb 4, 2015 at 14:36
  • ii libc6:amd64 2.13-38+deb7u7 amd64 Embedded GNU C Library: Shared libraries ad others libc dependences but ofc more then 500 characters :( Commented Feb 4, 2015 at 14:40
  • 2
    AAARGH! "This prints only 2 not other values" was extremely misleading. "This prints only several 2's, no other values ('2 2 2 2 2')". Of course "2 2 2 2 2" does not compare equal to "2". Apparently you also botched the error message by not writing exactly what was printed. Please do this very carefully next time you have a problem. Thanks. Commented Feb 4, 2015 at 22:10

4 Answers 4

3

Insert

echo "<$libc_main_ver>"

after the first line and the error will be obvious. Very likely there's a space or newline in there somewhere which you shouldn't numerically compare with 2.

Very esoteric: the problem could be the literal in -eq 2 as well. If it is followed by a carriage return character, I can somewhat reproduce your error message:

$ test "2" -eq 2^R
bash: test: 2: integer expression expected 

where ^R is a literal carriage return entered with CTRL-V CTRL-R. To verify or exclude this, run od -bc nameofyourscript

Sign up to request clarification or add additional context in comments.

6 Comments

ofcourse it print only 2.. i really continue to not understand what is the problem...
if i pull off the double quotes it gives me too many argouments error
@Nhoya If pulling off the quotes gives you a too many arguments error then $libc_main_ver contains more than just the string "2". Show us the output of this echo when added right before the failing comparison.
Maybe there are indeed invisible funny characters in there. To test, show us the result of echo "<$libc_main_ver>" | od -b
/foo ./foo: line 4: [: 2 2 2 2 2: integer expression expected 0000000 074 062 012 062 012 062 012 062 012 062 076 012 0000014
|
1

What if you tried this:

#!/bin/bash
libc_main_vers=$(dpkg -l | grep libc6 | awk '{ print $3 }' | awk -F . '{ print $1 }')
for ver in ${libc_main_vers}; do
    if (( ver == 2 )); then
        echo ok
    else
        echo nope
    fi
done
exit 0

9 Comments

Nope with -f 3 (libc6:amd64 libc6:i386 libc6-dev:amd64 libc6-i386 libc6-i686:i386 )it print name and architecture and with -f 2 nothing get parsed
@Nhoya, sorry, I don't have Ubuntu, so I am doing it blind folded based on what you posted in the comment. Is this the exact line for glibc: ii libc6:amd64 2.13-38+deb7u7 amd64 Embedded GNU C Library: Shared libraries?
Debian, not Ubuntu.. btw (ii libc6:amd64 2.13-38+deb7u7 amd64 Embedded GNU C Library: Shared libraries )
@Nhoya, I found a Mint box and found out there are multiple spaces in between the words, which is why the cut was failing. So I changed it to awk instead
ok, it works but it gives me only 1 result.. dpkg -l |grep libc6 gives me 4 lines then i need 4 "2" and not only one uuups head -n 4 10
|
1

Here is another version:

#!/bin/bash
libc_full=$(dpkg -l | grep libc6 | head -n 1 | awk '{ print $3 }')

libc_main=$(echo ${libc_full} | grep -o "^[0-9]*")
libc_update=$(echo ${libc_full} | grep -o "[0-9]*$")

if (( libc_main == 2 )); then
    echo "Main version is OK"
    if (( libc_update >= 7 )); then
        echo "Update version is OK"
        exit 0
    fi
fi
exit 1

Comments

0

It's unclear whether you require all the packages you list to have a major version number 2, or are just verifying that at least one of them does.

Anyway, if we start with the observation that grep foo | awk { print $1 } can usually be refactored into a single Awk script awk '/foo/ { print $1 }' we can already simplify your script; but it sometimes makes sense to refactor basically all of it into Awk. Perhaps like this:

dpkg -l 'libc6*' | awk '$3 !~ /^2\./ { exit 1 }' && echo ok || echo nope

If you are satisfied with just one package meeting the condition, change to something like

dpkg -l 'libc6*' | awk '$3 ~ /^2\./ { exit 0 } END { exit 1 }' && echo ok || echo nope

As always, foo && success || failure is a shorthand for

if foo; then
    success
else
    failure
fi

where the longhand probably makes sense if your real script needs to do something moderately more complex than just echo a value.

Do note that the output from dpkg -l is not necessarily suitable for scripts. Maybe use dpkg-query -f '${Version}\n' -W 'libc6' instead for robustness.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.