| ## @file |
| # Apply fixup to VTF binary image for FFS Raw section |
| # |
| # Copyright (c) 2008, Intel Corporation |
| # |
| # All rights reserved. This program and the accompanying materials |
| # are licensed and made available under the terms and conditions of the BSD License |
| # which accompanies this distribution. The full text of the license may be found at |
| # http://opensource.org/licenses/bsd-license.php |
| # |
| # THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, |
| # WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. |
| # |
| |
| import sys |
| |
| filename = sys.argv[1] |
| |
| if filename.lower().find('ia32') >= 0: |
| d = open(sys.argv[1], 'rb').read() |
| c = ((len(d) + 4 + 7) & ~7) - 4 |
| if c > len(d): |
| c -= len(d) |
| f = open(sys.argv[1], 'wb') |
| f.write('\x90' * c) |
| f.write(d) |
| f.close() |
| else: |
| from struct import pack |
| |
| PAGE_PRESENT = 0x01 |
| PAGE_READ_WRITE = 0x02 |
| PAGE_USER_SUPERVISOR = 0x04 |
| PAGE_WRITE_THROUGH = 0x08 |
| PAGE_CACHE_DISABLE = 0x010 |
| PAGE_ACCESSED = 0x020 |
| PAGE_DIRTY = 0x040 |
| PAGE_PAT = 0x080 |
| PAGE_GLOBAL = 0x0100 |
| PAGE_2M_MBO = 0x080 |
| PAGE_2M_PAT = 0x01000 |
| |
| def NopAlign4k(s): |
| c = ((len(s) + 0xfff) & ~0xfff) - len(s) |
| return ('\x90' * c) + s |
| |
| def PageDirectoryEntries4GbOf2MbPages(baseAddress): |
| |
| s = '' |
| for i in range(0x800): |
| i = ( |
| baseAddress + long(i << 21) + |
| PAGE_2M_MBO + |
| PAGE_CACHE_DISABLE + |
| PAGE_ACCESSED + |
| PAGE_DIRTY + |
| PAGE_READ_WRITE + |
| PAGE_PRESENT |
| ) |
| s += pack('Q', i) |
| return s |
| |
| def PageDirectoryPointerTable4GbOf2MbPages(pdeBase): |
| s = '' |
| for i in range(0x200): |
| i = ( |
| pdeBase + |
| (min(i, 3) << 12) + |
| PAGE_CACHE_DISABLE + |
| PAGE_ACCESSED + |
| PAGE_READ_WRITE + |
| PAGE_PRESENT |
| ) |
| s += pack('Q', i) |
| return s |
| |
| def PageMapLevel4Table4GbOf2MbPages(pdptBase): |
| s = '' |
| for i in range(0x200): |
| i = ( |
| pdptBase + |
| (min(i, 0) << 12) + |
| PAGE_CACHE_DISABLE + |
| PAGE_ACCESSED + |
| PAGE_READ_WRITE + |
| PAGE_PRESENT |
| ) |
| s += pack('Q', i) |
| return s |
| |
| def First4GbPageEntries(topAddress): |
| PDE = PageDirectoryEntries4GbOf2MbPages(0L) |
| pml4tBase = topAddress - 0x1000 |
| pdptBase = pml4tBase - 0x1000 |
| pdeBase = pdptBase - len(PDE) |
| PDPT = PageDirectoryPointerTable4GbOf2MbPages(pdeBase) |
| PML4T = PageMapLevel4Table4GbOf2MbPages(pdptBase) |
| return PDE + PDPT + PML4T |
| |
| def AlignAndAddPageTables(): |
| d = open(sys.argv[1], 'rb').read() |
| code = NopAlign4k(d) |
| topAddress = 0x100000000 - len(code) |
| d = ('\x90' * 4) + First4GbPageEntries(topAddress) + code |
| f = open(sys.argv[1], 'wb') |
| f.write(d) |
| f.close() |
| |
| AlignAndAddPageTables() |
| |