Hexadecimal To Decimal in Shell Script
Solution 1
To convert from hex to decimal, there are many ways to do it in the shell or with an external program:
With bash:
$ echo $((16#FF))
255
with bc:
$ echo "ibase=16; FF" | bc
255
with perl:
$ perl -le 'print hex("FF");'
255
with printf :
$ printf "%d\n" 0xFF
255
with python:
$ python -c 'print(int("FF", 16))'
255
with ruby:
$ ruby -e 'p "FF".to_i(16)'
255
with node.js:
$ nodejs <<< "console.log(parseInt('FF', 16))"
255
with rhino:
$ rhino<<EOF
print(parseInt('FF', 16))
EOF
...
255
with groovy:
$ groovy -e 'println Integer.parseInt("FF",16)'
255
Solution 2
Dealing with a very lightweight embedded version of busybox on Linux means many of the traditional commands are not available (bc, printf, dc, perl, python)
echo $((0x2f))
47
hexNum=2f
echo $((0x${hexNum}))
47
Credit to Peter Leung for this solution.
Solution 3
One more way to do it using the shell (bash or ksh, doesn't work with dash):
echo $((16#FF))
255
Solution 4
Various tools are available to you from within a shell. Sputnick has given you an excellent overview of your options, based on your initial question. He definitely deserves votes for the time he spent giving you multiple correct answers.
One more that's not on his list:
[ghoti@pc ~]$ dc -e '16i BFCA3000 p'
3217698816
But if all you want to do is subtract, why bother changing the input to base 10?
[ghoti@pc ~]$ dc -e '16i BFCA3000 17FF - p 10o p'
3217692673
BFCA1801
[ghoti@pc ~]$
The dc
command is "desk calc". It will also take input from stdin, like bc
, but instead of using "order of operations", it uses stacking ("reverse Polish") notation. You give it inputs which it adds to a stack, then give it operators that pop items off the stack, and push back on the results.
In the commands above we've got the following:
16i
-- tells dc to accept input in base 16 (hexadecimal). Doesn't change output base.BFCA3000
-- your initial number17FF
-- a random hex number I picked to subtract from your initial number-
-- take the two numbers we've pushed, and subtract the later one from the earlier one, then push the result back onto the stackp
-- print the last item on the stack. This doesn't change the stack, so...10o
-- tells dc to print its output in base "10", but remember that our input numbering scheme is currently hexadecimal, so "10" means "16".p
-- print the last item on the stack again ... this time in hex.
You can construct fabulously complex math solutions with dc. It's a good thing to have in your toolbox for shell scripts.
Solution 5
In dash and other shells, you can use
printf "%d\n" (your hexadecimal number)
to convert a hexadecimal number to decimal. This is not specific to bash or ksh.
Related videos on Youtube
VenkateshJN
Actively looking for full-time opportunities in the fields of Software Development, Data Mining & Machine Learning. Would like to work on interesting and challenging projects that would leverage my skills and provide me satisfaction of being useful to the society.
Updated on April 30, 2021Comments
-
VenkateshJN about 3 years
Can someone help me to convert a hexadecimal number to decimal number in a shell script?
E.g., I want to convert the hexadecimal number
bfca3000
to decimal using a shell script. I basically want the difference of two hexadecimal numbers.My code is:
var3=`echo "ibase=16; $var1" | bc` var4=`echo "ibase=16; $var2" | bc` var5=$(($var4-$var3)) # [Line 48]
When executing, I get this error:
Line 48: -: syntax error: operand expected (error token is "-")
-
Ciro Santilli OurBigBook.com over 9 yearsThe other way around: stackoverflow.com/questions/378829/…. Essentially the same tools. And possible cross site duplicate of: superuser.com/questions/226163/…
-
-
user1527227 almost 10 yearsWhat does the
#
symbol mean? Are there any other applications or documentation to read more about its use? -
Tomás Fox almost 10 yearsIt is mentioned here: link . At the end of section 6.5 it says: "...numbers take the form [base#]n, where the optional base is a decimal number between 2 and 64 representing the arithmetic base, and n is a number in that base. If base# is omitted, then base 10 is used. The digits greater than 9 are represented by the lowercase letters, the uppercase letters, ‘@’, and ‘_’, in that order. If base is less than or equal to 36, lowercase and uppercase letters may be used interchangeably to represent numbers between 10 and 35."
-
Ciro Santilli OurBigBook.com about 9 yearsIs the
printf
solution POSIX? If yes, it's the best :) -
Ruslan over 7 yearsIn bash you can also use
$((0xff))
, i.e. with C-like hex prefix instead of16#
, althoughN#
is clearly more general. -
roblogic about 6 yearsOK but beware of integer overflow error, e.g.
echo $((0x077E9F2DBF49D100001))
overflows the 64-biit integer limit of 2^64.bc
handles this properly -
roblogic about 6 yearsThe first bash example is susceptible to integer overflow error, e.g.
echo $((077E9F2DBF49D100001#FF))
overflows the 64-bit integer limit of 2^64.bc
handles this properly. -
lashgar over 5 yearse.g.
printf "%d" 0xff
-
Michael Shigorin over 5 yearslspci to xorg.conf PCI ID transform, just in case:
lspci -d ::0300 | cut -f1 -d' ' | ( IFS=":." read b d f; printf "PCI:%02d:%02d:%02d\n" 0x$b 0x$d 0x$f )
-
Gilles Quenot about 3 yearsThis syntax is discouraged by Chet Ramey himself. Use
$((0x3f))
-
Jeroen Wiert Pluimers about 3 yearsIndeed
echo
has limitations andbc
solves them, but Busybox does currently not havebc
among the applets. Hopefully it does in the future. -
Jeroen Wiert Pluimers about 3 years
-
frido about 3 yearsAlso solution for unsigned 64-bit values with
printf "%u" 0xff
-
Amruth A almost 3 yearssyntax error in expression (error token is "3")
-
user2240578 almost 2 years
bash ~ ➜ node <<< "console.log(0x1f)" 31