mirror of
				https://sourceware.org/git/glibc.git
				synced 2025-11-03 20:53:13 +03:00 
			
		
		
		
	
		
			
				
	
	
		
			94 lines
		
	
	
		
			3.4 KiB
		
	
	
	
		
			Python
		
	
	
	
	
	
			
		
		
	
	
			94 lines
		
	
	
		
			3.4 KiB
		
	
	
	
		
			Python
		
	
	
	
	
	
#!/usr/bin/python3
 | 
						|
# Regenerate <arch-syscall.h> and update syscall-names.list.
 | 
						|
# Copyright (C) 2020-2025 Free Software Foundation, Inc.
 | 
						|
# This file is part of the GNU C Library.
 | 
						|
#
 | 
						|
# The GNU C 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.1 of the License, or (at your option) any later version.
 | 
						|
#
 | 
						|
# The GNU C 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 the GNU C Library; if not, see
 | 
						|
# <http://www.gnu.org/licenses/>.
 | 
						|
 | 
						|
import argparse
 | 
						|
import io
 | 
						|
import os
 | 
						|
import sys
 | 
						|
 | 
						|
import glibcextract
 | 
						|
import glibcsyscalls
 | 
						|
 | 
						|
def atomic_replace(path, contents):
 | 
						|
    """Atomically replace PATH with CONTENTS, via a temporary file.
 | 
						|
 | 
						|
    The name of the temporary file is predictable, so locking is
 | 
						|
    required to avoid corruption.
 | 
						|
 | 
						|
    """
 | 
						|
    path_tmp = path + 'T'
 | 
						|
    with open(path_tmp, 'w') as tmp:
 | 
						|
        tmp.write(contents)
 | 
						|
    ok = False
 | 
						|
    try:
 | 
						|
        os.rename(path_tmp, path)
 | 
						|
        ok = True
 | 
						|
    finally:
 | 
						|
        # On error, try to delete the temporary file.
 | 
						|
        if not ok:
 | 
						|
            try:
 | 
						|
                os.unlink(path_tmp)
 | 
						|
            except:
 | 
						|
                pass
 | 
						|
 | 
						|
def main():
 | 
						|
    """The main entry point."""
 | 
						|
    parser = argparse.ArgumentParser(
 | 
						|
        description='System call list consistency checks')
 | 
						|
    parser.add_argument('--cc', metavar='CC', required=True,
 | 
						|
                        help='C compiler (including options) to use')
 | 
						|
    parser.add_argument('--lock', metavar='PATH', required=True,
 | 
						|
                        help='file to lock during the updates')
 | 
						|
    parser.add_argument('arch_syscall', metavar='ARCH-SYSCALL-H',
 | 
						|
                        help='The <arch-syscall.h> file to update')
 | 
						|
    parser.add_argument('names_list', metavar='SYSCALL-NAMES-LIST',
 | 
						|
                        help='The syscall name list to update ')
 | 
						|
 | 
						|
    args = parser.parse_args()
 | 
						|
 | 
						|
    kernel_constants = glibcsyscalls.kernel_constants(args.cc)
 | 
						|
 | 
						|
    with open(args.lock, 'r+') as lockfile:
 | 
						|
        os.lockf(lockfile.fileno(), os.F_LOCK, 0)
 | 
						|
 | 
						|
        # Replace <arch-syscall.h> with data derived from kernel headers.
 | 
						|
        # No merging is necessary here.  Arch-specific changes should go
 | 
						|
        # into <fixup-unistd-asm.h>.
 | 
						|
        out = io.StringIO()
 | 
						|
        out.write('/* AUTOGENERATED by update-syscall-lists.py.  */\n')
 | 
						|
        for name, value in sorted(kernel_constants.items()):
 | 
						|
            out.write('#define __NR_{} {}\n'.format(name, value))
 | 
						|
        atomic_replace(args.arch_syscall, out.getvalue())
 | 
						|
 | 
						|
        # Merge the architecture-specific system call names into the
 | 
						|
        # global names list, syscall-names.list.  This file contains names
 | 
						|
        # from other architectures (and comments), so it is necessary to
 | 
						|
        # merge the existing files with the names obtained from the
 | 
						|
        # kernel.
 | 
						|
        with open(args.names_list, 'r') as list_file:
 | 
						|
            names_list = glibcsyscalls.SyscallNamesList(list_file)
 | 
						|
        merged = names_list.merge(kernel_constants.keys())
 | 
						|
        out = io.StringIO()
 | 
						|
        for line in merged:
 | 
						|
            out.write(line)
 | 
						|
        atomic_replace(args.names_list, out.getvalue())
 | 
						|
 | 
						|
if __name__ == '__main__':
 | 
						|
    main()
 |