2018-04-19 16:58:51 +03:00
#!/usr/bin/python3
2015-05-27 05:28:29 +03:00
#
# Copyright (C) 2015 Red Hat
#
# This library is free software; you can redistribute it and/or
# modify it under the terms of the GNU Lesser General Public
# License as published by the Free Software Foundation; either
# version 2 of the License, or (at your option) any later version.
#
# This library is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
# Lesser General Public License for more details.
#
# You should have received a copy of the GNU Lesser General Public
# License along with this library; if not, write to the
# Free Software Foundation, Inc., 59 Temple Place - Suite 330,
# Boston, MA 02111-1307, USA.
import os
import sys
2018-04-19 16:58:51 +03:00
import functools
2015-05-27 05:28:29 +03:00
if len ( sys . argv ) == 1 :
loaderpath = ' /boot/loader/entries '
grub2path = ' /boot/grub2/grub.cfg '
else :
loaderpath = sys . argv [ 1 ]
grub2path = sys . argv [ 2 ]
def fatal ( msg ) :
sys . stderr . write ( msg )
sys . stderr . write ( ' \n ' )
sys . exit ( 1 )
def compare_entries_descending ( a , b ) :
return int ( b [ ' version ' ] ) - int ( a [ ' version ' ] )
def get_ostree_option ( optionstring ) :
for o in optionstring . split ( ) :
if o . startswith ( ' ostree= ' ) :
return o [ 8 : ]
raise ValueError ( ' ostree= not found ' )
2018-04-19 16:58:51 +03:00
2015-05-27 05:28:29 +03:00
entries = [ ]
grub2_entries = [ ]
# Parse loader configs
for fname in os . listdir ( loaderpath ) :
path = os . path . join ( loaderpath , fname )
with open ( path ) as f :
entry = { }
for line in f :
line = line . strip ( )
if ( line == ' ' or line . startswith ( ' # ' ) ) :
continue
s = line . find ( ' ' )
assert s > 0
k = line [ 0 : s ]
v = line [ s + 1 : ]
entry [ k ] = v
entries . append ( entry )
2018-04-19 16:58:51 +03:00
entries . sort ( key = functools . cmp_to_key ( compare_entries_descending ) )
2015-05-27 05:28:29 +03:00
# Parse GRUB2 config
with open ( grub2path ) as f :
in_ostree_config = False
grub2_entry = None
for line in f :
if line . startswith ( ' ### BEGIN /etc/grub.d/15_ostree ### ' ) :
in_ostree_config = True
2018-04-19 16:58:51 +03:00
elif line . startswith ( ' ### END /etc/grub.d/15_ostree ### ' ) :
2015-05-27 05:28:29 +03:00
in_ostree_config = False
if grub2_entry is not None :
grub2_entries . append ( grub2_entry )
elif in_ostree_config :
if line . startswith ( ' menuentry ' ) :
if grub2_entry is not None :
grub2_entries . append ( grub2_entry )
grub2_entry = { }
elif line . startswith ( ' linux ' ) :
parts = line . split ( )
grub2_entry [ ' linux ' ] = parts [ 1 ]
grub2_entry [ ' options ' ] = ' ' . join ( parts [ 2 : ] )
elif line . startswith ( ' initrd ' ) :
grub2_entry [ ' initrd ' ] = line . split ( ) [ 1 ]
if len ( entries ) != len ( grub2_entries ) :
fatal ( " Found {0} loader entries, but {1} GRUB2 entries \n " . format ( len ( entries ) , len ( grub2_entries ) ) )
def assert_matches_key ( a , b , key ) :
aval = a [ key ]
bval = b [ key ]
if aval != bval :
fatal ( " Mismatch on {0} : {1} != {2} " . format ( key , aval , bval ) )
for i , ( entry , grub2entry ) in enumerate ( zip ( entries , grub2_entries ) ) :
assert_matches_key ( entry , grub2entry , ' linux ' )
assert_matches_key ( entry , grub2entry , ' initrd ' )
entry_ostree = get_ostree_option ( entry [ ' options ' ] )
grub2_ostree = get_ostree_option ( grub2entry [ ' options ' ] )
if entry_ostree != grub2_ostree :
fatal ( " Mismatch on ostree option: {0} != {1} " . format ( entry_ostree , grub2_ostree ) )
sys . stdout . write ( ' GRUB2 configuration validated \n ' )
sys . exit ( 0 )