I'm trying to create an array that looks like this:
0 kernel
1 /boot/vmlinuz-4.8.0-1.el7.elrepo.x86_64
2 kernel
3 /boot/vmlinuz-4.7.3-1.el7.elrepo.x86_64
Using the grubby command of which the ouput for the entires I'm looking for are:
index=2
kernel=/boot/vmlinuz-4.8.0-1.el7.elrepo.x86_64
root=/dev/mapper/<my_vol>-root
initrd=/boot/initramfs-4.8.0-1.el7.elrepo.x86_64.img
title=CentOS Linux (4.8.0-1.el7.elrepo.x86_64) 7 (Core)
index=3
kernel=/boot/vmlinuz-4.7.3-1.el7.elrepo.x86_64
root=/dev/mapper/<my_vol>-root
initrd=/boot/initramfs-4.7.3-1.el7.elrepo.x86_64.img
title=CentOS Linux (4.7.3-1.el7.elrepo.x86_64) 7 (Core)
(I've removed the "args=" line for sanitisation purposes)
When I try to use the following command which works... (err... for the first 2 elements of the array). It decided that 2 indicies should be squashed into one.
IFS='=' read -a KERNELS <<< $(sudo grubby --info=ALL |grep -v rescue |grep -E 4.[78] |grep kernel)
0 kernel
1 /boot/vmlinuz-4.8.0-1.el7.elrepo.x86_64 kernel
2 /boot/vmlinuz-4.7.3-1.el7.elrepo.x86_64
First of why is it doing this? And how can I fix it?
I understand that there are other ways I could solve this problem but I want to understand what's going on here:
for i in ${KERNELS[@]}; do echo $i; done
kernel
/boot/vmlinuz-4.8.0-1.el7.elrepo.x86_64
kernel
/boot/vmlinuz-4.7.3-1.el7.elrepo.x86_64
for i in ${!KERNELS[@]}; do echo $i ${KERNELS[$i]}; done
0 kernel
1 /boot/vmlinuz-4.8.0-1.el7.elrepo.x86_64 kernel
2 /boot/vmlinuz-4.7.3-1.el7.elrepo.x86_64
I suspect it has something to do with the fact that when you run
sudo grubby --info=ALL |grep -v rescue |grep -E 4.[78] |grep kernel
kernel=/boot/vmlinuz-4.8.0-1.el7.elrepo.x86_64
kernel=/boot/vmlinuz-4.7.3-1.el7.elrepo.x86_64
You get two lines of output and the IFS= is separating on '=' and ignoring the '\n'
I've tried using awk '{print}' ORS=' ' ideas to output everything on one line but it gets messy.
There has to be a more elegant way to use the hereto string with multiple lines of output. Surely...
greppipeline seems to beg for an Awk solution.grubby --info=ALL | awk 'BEGIN { ORS="=" } !/rescue/ && /4\.[78]/ && /kernel/'-- notice also the requirement to backslash a literal period, and see also useless use ofgrepfor i in ${!KERNELS[@]}; do echo "$i" "${KERNELS[i]}"; done. You'll see that${KERNELS[1]}contains the newline that separates the two lines in the output of the pipeline. A here-string isn't appropriate here. (Also, what version ofbashare you using? A bug dealing with pre-command environment settings and here-strings that wasn't completely fixed untilbash4.4 may be affecting your results.)