[device/Arista] Improvements to the boot of Arista devices. (#2898)

* Fix showing systemd shutdown sequence when verbose is set

* Fix creation of kernel-cmdline file

Sometimes boot0 prints error
"mv: can't preserve ownership of '/mnt/flash/image-arsonic.xxxx/kernel-cmdline': Operation not permitted"

* Improve flash space usage during installation

Some older systems only have 2GB of flash available. Installing a second
image on these can prove to be challenging.
The new installation process moves the installer swi to memory in order
to avoid free up space from the flash before uncompressing it there.
It removes all the flash space usage spike and also improves the IO
since the installation is no more reading and writting to the flash at
the same time.

* Add support of 7060CX-32S-SSD

* 7260CX3: use inventory powerCycle procedures

* 7050QX-32S: use inventory powerCycle procedures

* 7050QX-32: use inventory powerCycle procedures

* platform: arista: add common platform_reboot

Replace platform_reboot by a link to new common for devices already
using a similar script.

* 7060CX-32S: use inventory powerCycle procedures

* Install python smbus in pmon

Some platform plugin need the python smbus library to perform some actions.
This installs the dependency.
This commit is contained in:
Samuel Angebault 2019-05-15 12:45:06 -07:00 committed by lguohan
parent 83e74d6dbb
commit 77cde50541
9 changed files with 56 additions and 309 deletions

View File

@ -1,87 +0,0 @@
#!/usr/bin/env python
# Copyright (c) 2018 Arista Networks, Inc. All rights reserved.
# Arista Networks, Inc. Confidential and Proprietary.
# Reboot script for 7050QX-32
from __future__ import print_function
import sys
import mmap, os
import subprocess
from struct import pack, unpack
class MmapResource( object ):
"""Resource implementation for a directly-mapped memory region."""
def __init__( self, path ):
try:
fd = os.open( path, os.O_RDWR )
except EnvironmentError:
print( "FAIL can not open scd memory-map resource file" )
print( "FAIL are you running on the proper platform?" )
sys.exit( 1 )
try:
size = os.fstat( fd ).st_size
except EnvironmentError:
print( "FAIL can not fstat scd memory-map resource file" )
print( "FAIL are you running on the proper platform?" )
sys.exit( 1 )
try:
self.mmap_ = mmap.mmap( fd, size, mmap.MAP_SHARED,
mmap.PROT_READ | mmap.PROT_WRITE )
except EnvironmentError:
print( "FAIL can not map scd memory-map file" )
print( "FAIL are you running on the proper platform?" )
sys.exit( 1 )
finally:
try:
# Note that closing the file descriptor has no effect on the memory map
os.close( fd )
except EnvironmentError:
print( "FAIL failed to close scd memory-map file" )
sys.exit( 1 )
def read32( self, addr ):
return unpack( '<L', self.mmap_[ addr : addr + 4 ] )[ 0 ]
def write32( self, addr, value ):
self.mmap_[ addr: addr + 4 ] = pack( '<L', value )
def scdRegTest( scd, offset, val1, count ):
scd.write32( offset, val1 )
val2 = scd.read32( offset )
if val1 != val2:
print( "FAIL: scd write 0x%08x but read back 0x%08x in iter %d" %
( val1, val2, count ) )
sys.exit( 17 )
def scdScrRegTest( scd ):
scrOffset = 0x0130
for i in range( 0, 3 ):
scdRegTest( scd, scrOffset, 0xdeadbeef, i )
scdRegTest( scd, scrOffset, 0xa5a5a5a5, i )
scdRegTest( scd, scrOffset, 0x00000000, i )
def reboot( scd ):
# reboot the system by writing to register 0x7000
print( "Rebooting" )
scd.write32( 0x7000, 0xDEAD )
print( "REBOOTED" )
def main():
busName = "/sys/bus/pci/devices/0000:04:00.0/resource0"
subprocess.call( [ 'modprobe', 'scd' ] )
scd = MmapResource( busName )
#
# verify that we can read/write scd scratch register
#
scdScrRegTest( scd )
# reboot the system
reboot( scd )
if __name__ == "__main__":
main()

View File

@ -0,0 +1 @@
../x86_64-arista_common/platform_reboot

View File

@ -1,87 +0,0 @@
#!/usr/bin/env python
# Copyright (c) 2018 Arista Networks, Inc. All rights reserved.
# Arista Networks, Inc. Confidential and Proprietary.
# Reboot script for 7050QX-32S
from __future__ import print_function
import sys
import mmap, os
import subprocess
from struct import pack, unpack
class MmapResource( object ):
"""Resource implementation for a directly-mapped memory region."""
def __init__( self, path ):
try:
fd = os.open( path, os.O_RDWR )
except EnvironmentError:
print( "FAIL can not open scd memory-map resource file" )
print( "FAIL are you running on the proper platform?" )
sys.exit( 1 )
try:
size = os.fstat( fd ).st_size
except EnvironmentError:
print( "FAIL can not fstat scd memory-map resource file" )
print( "FAIL are you running on the proper platform?" )
sys.exit( 1 )
try:
self.mmap_ = mmap.mmap( fd, size, mmap.MAP_SHARED,
mmap.PROT_READ | mmap.PROT_WRITE )
except EnvironmentError:
print( "FAIL can not map scd memory-map file" )
print( "FAIL are you running on the proper platform?" )
sys.exit( 1 )
finally:
try:
# Note that closing the file descriptor has no effect on the memory map
os.close( fd )
except EnvironmentError:
print( "FAIL failed to close scd memory-map file" )
sys.exit( 1 )
def read32( self, addr ):
return unpack( '<L', self.mmap_[ addr : addr + 4 ] )[ 0 ]
def write32( self, addr, value ):
self.mmap_[ addr: addr + 4 ] = pack( '<L', value )
def scdRegTest( scd, offset, val1, count ):
scd.write32( offset, val1 )
val2 = scd.read32( offset )
if val1 != val2:
print( "FAIL: scd write 0x%08x but read back 0x%08x in iter %d" %
( val1, val2, count ) )
sys.exit( 17 )
def scdScrRegTest( scd ):
scrOffset = 0x0130
for i in range( 0, 3 ):
scdRegTest( scd, scrOffset, 0xdeadbeef, i )
scdRegTest( scd, scrOffset, 0xa5a5a5a5, i )
scdRegTest( scd, scrOffset, 0x00000000, i )
def reboot( scd ):
# reboot the system by writing to register 0x7000
print( "Rebooting" )
scd.write32( 0x7000, 0xDEAD )
print( "REBOOTED" )
def main():
busName = "/sys/bus/pci/devices/0000:02:00.0/resource0"
subprocess.call( [ 'modprobe', 'scd' ] )
scd = MmapResource( busName )
#
# verify that we can read/write scd scratch register
#
scdScrRegTest( scd )
# reboot the system
reboot( scd )
if __name__ == "__main__":
main()

View File

@ -0,0 +1 @@
../x86_64-arista_common/platform_reboot

View File

@ -1,18 +0,0 @@
#!/usr/bin/env python
# Copyright (c) 2018 Arista Networks, Inc. All rights reserved.
# Arista Networks, Inc. Confidential and Proprietary.
# Reboot script for 7060CX-32
from __future__ import print_function
import smbus
def main():
print( "Rebooting" )
bus = smbus.SMBus( 1 )
bus.write_byte_data( 0x23, 0x04, 0xde )
print( "REBOOTED" )
if __name__ == "__main__":
main()

View File

@ -0,0 +1 @@
../x86_64-arista_common/platform_reboot

View File

@ -1,11 +0,0 @@
#!/usr/bin/env python
from arista import platforms
from arista.utils.sonic_reboot import reboot
def main():
# reboot the system
reboot()
if __name__ == "__main__":
main()

View File

@ -0,0 +1 @@
../x86_64-arista_common/platform_reboot

View File

@ -1,11 +0,0 @@
#!/usr/bin/env python
import arista.platforms
from arista.utils.sonic_reboot import reboot
def main():
# reboot the system
reboot()
if __name__ == "__main__":
main()

View File

@ -0,0 +1 @@
../x86_64-arista_common/platform_reboot

View File

@ -1,87 +0,0 @@
#!/usr/bin/env python
# Copyright (c) 2018 Arista Networks, Inc. All rights reserved.
# Arista Networks, Inc. Confidential and Proprietary.
# Reboot script for 7260CX3
from __future__ import print_function
import sys
import mmap, os
import subprocess
from struct import pack, unpack
class MmapResource( object ):
"""Resource implementation for a directly-mapped memory region."""
def __init__( self, path ):
try:
fd = os.open( path, os.O_RDWR )
except EnvironmentError:
print( "FAIL can not open scd memory-map resource file" )
print( "FAIL are you running on the proper platform?" )
sys.exit( 1 )
try:
size = os.fstat( fd ).st_size
except EnvironmentError:
print( "FAIL can not fstat scd memory-map resource file" )
print( "FAIL are you running on the proper platform?" )
sys.exit( 1 )
try:
self.mmap_ = mmap.mmap( fd, size, mmap.MAP_SHARED,
mmap.PROT_READ | mmap.PROT_WRITE )
except EnvironmentError:
print( "FAIL can not map scd memory-map file" )
print( "FAIL are you running on the proper platform?" )
sys.exit( 1 )
finally:
try:
# Note that closing the file descriptor has no effect on the memory map
os.close( fd )
except EnvironmentError:
print( "FAIL failed to close scd memory-map file" )
sys.exit( 1 )
def read32( self, addr ):
return unpack( '<L', self.mmap_[ addr : addr + 4 ] )[ 0 ]
def write32( self, addr, value ):
self.mmap_[ addr: addr + 4 ] = pack( '<L', value )
def scdRegTest( scd, offset, val1, count ):
scd.write32( offset, val1 )
val2 = scd.read32( offset )
if val1 != val2:
print( "FAIL: scd write 0x%08x but read back 0x%08x in iter %d" %
( val1, val2, count ) )
sys.exit( 17 )
def scdScrRegTest( scd ):
scrOffset = 0x0130
for i in range( 0, 3 ):
scdRegTest( scd, scrOffset, 0xdeadbeef, i )
scdRegTest( scd, scrOffset, 0xa5a5a5a5, i )
scdRegTest( scd, scrOffset, 0x00000000, i )
def reboot( scd ):
# reboot the system by writing to register 0x7000
print( "Rebooting" )
scd.write32( 0x7000, 0xDEAD )
print( "REBOOTED" )
def main():
busName = "/sys/bus/pci/devices/0000:ff:0b.3/resource0"
subprocess.call( [ 'modprobe', 'scd' ] )
scd = MmapResource( busName )
#
# verify that we can read/write scd scratch register
#
scdScrRegTest( scd )
# reboot the system
reboot( scd )
if __name__ == "__main__":
main()

View File

@ -0,0 +1 @@
../x86_64-arista_common/platform_reboot

View File

@ -0,0 +1,11 @@
#!/usr/bin/env python
import arista.platforms
from arista.utils.sonic_reboot import reboot
def main():
# reboot the system
reboot()
if __name__ == "__main__":
main()

View File

@ -7,7 +7,7 @@ RUN [ -f /etc/rsyslog.conf ] && sed -ri "s/%syslogtag%/$docker_container_name#%s
ENV DEBIAN_FRONTEND=noninteractive
# Install required packages
RUN apt-get update && apt-get install -y python-pip libpython2.7 ipmitool librrd8 librrd-dev rrdtool
RUN apt-get update && apt-get install -y python-pip libpython2.7 ipmitool librrd8 librrd-dev rrdtool python-smbus
{% if docker_platform_monitor_debs.strip() -%}
# Copy locally-built Debian package dependencies

View File

@ -68,6 +68,8 @@ cmdline_base="$target_path/kernel-params-base"
cmdline_image="$image_path/kernel-cmdline"
boot_config="$target_path/boot-config"
swi_tmpfs="/tmp/tmp-swi"
bootconfigvars="KERNEL INITRD CONSOLESPEED PASSWORD NETDEV NETAUTO NETIP NETMASK NETGW NETDOMAIN NETDNS NETHW memtest"
flash_re=" /mnt/flash| /host"
@ -126,9 +128,34 @@ update_next_boot() {
fi
}
move_swi_to_tmpfs() {
local oldswi="$1"
local newswi="$swi_tmpfs/$(basename $oldswi)"
mkdir -p "$swi_tmpfs"
if ! $in_aboot && ! mount | grep -q ' /tmp type tmpfs'; then
# mount a real tmpfs on /tmp/tmp-swi if /tmp is not one already.
mount -t tmpfs tmp-swi "$swi_tmpfs"
fi
mv "$oldswi" "$newswi"
echo "$newswi"
}
cleanup_swi_tmpfs() {
rm -f "$swipath"
if mount | grep -q "$swi_tmpfs"; then
umount "$swi_tmpfs" || :
fi
}
extract_image() {
mkdir -p "$image_path"
info "Moving swi to a tmpfs"
## Avoid problematic flash usage spike on older systems, also improves I/O
swipath="$(move_swi_to_tmpfs $swipath)"
info "Extracting swi content"
## Unzip the image except boot0 and dockerfs archive
unzip -oq "$swipath" -x boot0 "$dockerfs" -d "$image_path"
@ -146,7 +173,6 @@ extract_image() {
fi
## extract docker archive
info "Unpacking $dockerfs"
unzip -oqp "$swipath" "$dockerfs" | tar xzf - -C "$image_path/{{ DOCKERFS_DIR }}" $TAR_EXTRA_OPTION
else
## save dockerfs archive in the image directory
@ -154,14 +180,15 @@ extract_image() {
info "Unpacking $dockerfs delayed to initrd because $target_path is $rootfs_type"
fi
## remove installer since it's not needed anymore
info "Remove installer"
cleanup_swi_tmpfs
## use new reduced-size boot swi
local swi_boot_path="flash:$image_name/{{ ABOOT_BOOT_IMAGE }}"
update_boot_config SWI "$swi_boot_path"
update_boot_config SWI_DEFAULT "$swi_boot_path"
## Remove installer swi as it has lots of redundunt contents
rm -f "$swipath"
## sync disk operations
sync
}
@ -205,7 +232,8 @@ platform_specific() {
flash_size=3700
echo "modprobe.blacklist=radeon,sp5100_tco" >>/tmp/append
fi
if [ "$sid" = "Upperlake" ] || [ "$sid" = "UpperlakeES" ]; then
if [ "$sid" = "Upperlake" ] || [ "$sid" = "UpperlakeES" ] ||
[ "$sid" = "UpperlakeSsd" ]; then
aboot_machine=arista_7060_cx32s
flash_size=3700
echo "amd_iommu=off" >> /tmp/append
@ -304,7 +332,7 @@ write_boot_configs() {
fi
fi
mv /tmp/append $cmdline_image
cat /tmp/append > $cmdline_image
[ -e ${target_path}/machine.conf ] || write_machine_config
}
@ -313,7 +341,10 @@ run_kexec() {
local kernel="${KERNEL:-$(find $image_path/boot -name 'vmlinuz-*' -type f | head -n 1)}"
local initrd="${INITRD:-$(find $image_path/boot -name 'initrd.img-*' -type f | head -n 1)}"
if ! $verbose; then
if $verbose; then
# show systemd showdown sequence when verbose is set
cmdline="$cmdline systemd.show_status=true"
else
# Start showing systemd information from the first failing unit if any.
# systemd.show_status=false or quiet can be used to silence systemd entierly
cmdline="$cmdline systemd.show_status=auto"