Created
August 27, 2013 13:34
-
-
Save badp/6353579 to your computer and use it in GitHub Desktop.
Check XEN CPUIDs for vailidity. I didn't end up using this code, so here it is under the WTFPL.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import re | |
import unittest | |
def IsValidXenCPUID(cpuid_mask): | |
# host(,[0-9a-z]+=([a-z]|[0-9])+)* | |
libxl_syntax = re.compile(r""" | |
host #required header | |
( #plus many of the following: | |
, #comma separator | |
[0-9a-z]+ #field name | |
= #set to | |
([a-z]|[0-9]+) #a single character or a numeric value | |
)* | |
$ #and nothing else | |
""", re.VERBOSE | re.MULTILINE | re.IGNORECASE) | |
xend_fudge_item_re = r""" | |
e[a-d]x= #register of the call return value to fudge | |
( | |
0x[0-9A-F]{1,8} #either hardcode the reply | |
| [10xks]{32} #or edit the bitfield directly | |
) | |
""" | |
xend_string_item_re = r""" | |
( #leafnum (the contents of EAX before the call) | |
\d+(,\d+)? | #in number format (or number,number - see [0]) | |
0x[0-9A-F]{1,8} #or in hex format | |
) | |
: #separator; no whitespace here | |
%s #one fudge | |
( | |
\s* #whitespace between n-th fudge and separator | |
, #comma separator | |
\s* #whitespace between seperator and n+1-th separator | |
%s #another fudge | |
)* #repeated multiple times | |
""" % (xend_fudge_item_re, xend_fudge_item_re) | |
# [0]: http://zhigang.org/wiki/XenCPUID#cpuid-overridden-for-xen-guests | |
xend_syntax = re.compile(r""" | |
\s* #whitespace at the very start | |
\[ #a list of | |
\s* #whitespace inside the list, before first element | |
'%s' #string elements | |
( | |
\s* #whitespace between n-th item and separator | |
, #separator | |
\s* #whitespace between separator and n+1-th item | |
'%s' | |
)* #repeated multiple times | |
\s* #whitespace inside the list, after last element | |
\] #end of list | |
\s* #whitespace after the list | |
$ #and nothing else | |
""" % (xend_string_item_re, xend_string_item_re), | |
re.VERBOSE | re.MULTILINE | re.IGNORECASE) | |
return ( | |
not cpuid_mask # nothing to validate | |
or libxl_syntax.match(cpuid_mask) # it is valid libxl syntax | |
or xend_syntax.match(cpuid_mask) # it is valid xend syntax | |
) | |
class TestXenCpuidSyntaxVerify(unittest.TestCase): | |
def TestLibxlSyntax(): | |
"""Accept Libxl syntax example from documentation. | |
Test sources: | |
* http://xenbits.xen.org/docs/unstable/man/xl.cfg.5.html""" | |
self.assertTrue(IsValidXenCPUID( | |
"host,tm=0,sse3=0" | |
)) | |
def TestXendSyntax(): | |
"""Accept Libxl syntax example from documentation. | |
Test sources: | |
* http://xenbits.xen.org/docs/unstable/man/xl.cfg.5.html | |
* http://zhigang.org/wiki/XenCPUID#cpuid-overridden-for-xen-guests | |
* https://code.google.com/p/ganeti/issues/detail?id=159""" | |
#Base example | |
self.assertTrue(hv_xen.IsValidXenCPUID( | |
"['1:ecx=xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx0']" | |
)) | |
#More whitespace | |
self.assertTrue(hv_xen.IsValidXenCPUID( | |
"[ '1:ecx=xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx0,edx=xx0xxxxxxxxxxxxxxxxxxxxxxxxxxxxx' ]" | |
)) | |
#MORE whitespace | |
self.assertTrue(hv_xen.IsValidXenCPUID( | |
"""[ '1:ecx=xxxxxxxxxxx00xxxxxxxxxxxxxxxxxxx, | |
eax=xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx' ]""" | |
)) | |
#Number, number leafnum format. | |
self.assertTrue(hv_xen.IsValidXenCPUID( | |
"""['1:edx=xxx1xxxxxxxxxxxxxxxxxxxxxxxxxxxx, | |
ebx=xxxxxxxx00010000xxxxxxxxxxxxxxxx', | |
'4,0:eax=001111xxxxxxxxxxxxxxxxxxxxxxxxxx']""" | |
)) | |
#hexadecimal leafnum format | |
self.assertTrue(hv_xen.IsValidXenCPUID( | |
"""['1:ebx=xxxxxxxx00001010xxxxxxxxxxxxxxxx, | |
edx=xxx1xxxxxxxxxxxxxxxxxxxxxxxxxxxx', | |
'0x80000001:ecx=xxxxxxxxxxxxxxxxxxxxxxxxxxxxxx1x', | |
'0x80000008:ecx=xxxxxxxxxxxxxxxxxxxxxxxxxx001001']""" | |
)) | |
# Hex fudging | |
# This is found on the zhigang file, but it is actually wrong. The bitfields | |
# only have 31 bits in them. The patch in bug 159 by furlongm fixes this by | |
# adding one extra 'x' at the start of the bitfield, bringing it to 32 bits. | |
self.assertFalse(hv_xen.IsValidXenCPUID( | |
"""[ '0:eax=0x3,ebx=0x0,ecx=0x0,edx=0x0', | |
'1:eax=0x06b1, | |
ecx=xxxxxxxxxx0000xx00xxx0000000xx0, | |
edx=xx00000xxxxxxx0xxxxxxxxx0xxxxxx', | |
'4:eax=0x3,ebx=0x0,ecx=0x0,edx=0x0', | |
'0x80000000:eax=0x3,ebx=0x0,ecx=0x0,edx=0x0']""" | |
)) | |
#This is the corrected version. | |
self.assertTrue(hv_xen.IsValidXenCPUID( | |
"""[ '0:eax=0x3,ebx=0x0,ecx=0x0,edx=0x0', | |
'1:eax=0x06b1, | |
ecx=xxxxxxxxxxx0000xx00xxx0000000xx0, | |
edx=xxx00000xxxxxxx0xxxxxxxxx0xxxxxx', | |
'4:eax=0x3,ebx=0x0,ecx=0x0,edx=0x0', | |
'0x80000000:eax=0x3,ebx=0x0,ecx=0x0,edx=0x0']""" | |
)) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment