diff options
author | Srikant Patnaik | 2015-01-11 12:28:04 +0530 |
---|---|---|
committer | Srikant Patnaik | 2015-01-11 12:28:04 +0530 |
commit | 871480933a1c28f8a9fed4c4d34d06c439a7a422 (patch) | |
tree | 8718f573808810c2a1e8cb8fb6ac469093ca2784 /ANDROID_3.4.5/arch/s390/kernel | |
parent | 9d40ac5867b9aefe0722bc1f110b965ff294d30d (diff) | |
download | FOSSEE-netbook-kernel-source-871480933a1c28f8a9fed4c4d34d06c439a7a422.tar.gz FOSSEE-netbook-kernel-source-871480933a1c28f8a9fed4c4d34d06c439a7a422.tar.bz2 FOSSEE-netbook-kernel-source-871480933a1c28f8a9fed4c4d34d06c439a7a422.zip |
Moved, renamed, and deleted files
The original directory structure was scattered and unorganized.
Changes are basically to make it look like kernel structure.
Diffstat (limited to 'ANDROID_3.4.5/arch/s390/kernel')
82 files changed, 0 insertions, 28939 deletions
diff --git a/ANDROID_3.4.5/arch/s390/kernel/Makefile b/ANDROID_3.4.5/arch/s390/kernel/Makefile deleted file mode 100644 index 884b18af..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/Makefile +++ /dev/null @@ -1,61 +0,0 @@ -# -# Makefile for the linux kernel. -# - -ifdef CONFIG_FUNCTION_TRACER -# Don't trace early setup code and tracing code -CFLAGS_REMOVE_early.o = -pg -CFLAGS_REMOVE_ftrace.o = -pg -endif - -# -# Passing null pointers is ok for smp code, since we access the lowcore here. -# -CFLAGS_smp.o := -Wno-nonnull - -# -# Pass UTS_MACHINE for user_regset definition -# -CFLAGS_ptrace.o += -DUTS_MACHINE='"$(UTS_MACHINE)"' - -CFLAGS_sysinfo.o += -Iinclude/math-emu -Iarch/s390/math-emu -w - -obj-y := bitmap.o traps.o time.o process.o base.o early.o setup.o vtime.o \ - processor.o sys_s390.o ptrace.o signal.o cpcmd.o ebcdic.o nmi.o \ - debug.o irq.o ipl.o dis.o diag.o mem_detect.o sclp.o vdso.o \ - sysinfo.o jump_label.o lgr.o os_info.o - -obj-y += $(if $(CONFIG_64BIT),entry64.o,entry.o) -obj-y += $(if $(CONFIG_64BIT),reipl64.o,reipl.o) - -extra-y += head.o init_task.o vmlinux.lds -extra-y += $(if $(CONFIG_64BIT),head64.o,head31.o) - -obj-$(CONFIG_MODULES) += s390_ksyms.o module.o -obj-$(CONFIG_SMP) += smp.o -obj-$(CONFIG_SCHED_BOOK) += topology.o -obj-$(CONFIG_HIBERNATION) += suspend.o swsusp_asm64.o -obj-$(CONFIG_AUDIT) += audit.o -compat-obj-$(CONFIG_AUDIT) += compat_audit.o -obj-$(CONFIG_COMPAT) += compat_linux.o compat_signal.o \ - compat_wrapper.o compat_exec_domain.o \ - $(compat-obj-y) - -obj-$(CONFIG_STACKTRACE) += stacktrace.o -obj-$(CONFIG_KPROBES) += kprobes.o -obj-$(CONFIG_FUNCTION_TRACER) += $(if $(CONFIG_64BIT),mcount64.o,mcount.o) -obj-$(CONFIG_DYNAMIC_FTRACE) += ftrace.o -obj-$(CONFIG_FUNCTION_GRAPH_TRACER) += ftrace.o -obj-$(CONFIG_FTRACE_SYSCALLS) += ftrace.o -obj-$(CONFIG_CRASH_DUMP) += crash_dump.o -obj-$(CONFIG_PERF_EVENTS) += perf_event.o perf_cpum_cf.o - -# Kexec part -S390_KEXEC_OBJS := machine_kexec.o crash.o -S390_KEXEC_OBJS += $(if $(CONFIG_64BIT),relocate_kernel64.o,relocate_kernel.o) -obj-$(CONFIG_KEXEC) += $(S390_KEXEC_OBJS) - -# vdso -obj-$(CONFIG_64BIT) += vdso64/ -obj-$(CONFIG_32BIT) += vdso32/ -obj-$(CONFIG_COMPAT) += vdso32/ diff --git a/ANDROID_3.4.5/arch/s390/kernel/asm-offsets.c b/ANDROID_3.4.5/arch/s390/kernel/asm-offsets.c deleted file mode 100644 index 83e6edf5..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/asm-offsets.c +++ /dev/null @@ -1,163 +0,0 @@ -/* - * Generate definitions needed by assembly language modules. - * This code generates raw asm output which is post-processed to extract - * and format the required data. - */ - -#define ASM_OFFSETS_C - -#include <linux/kbuild.h> -#include <linux/sched.h> -#include <asm/cputime.h> -#include <asm/timer.h> -#include <asm/vdso.h> -#include <asm/pgtable.h> - -/* - * Make sure that the compiler is new enough. We want a compiler that - * is known to work with the "Q" assembler constraint. - */ -#if __GNUC__ < 3 || (__GNUC__ == 3 && __GNUC_MINOR__ < 3) -#error Your compiler is too old; please use version 3.3.3 or newer -#endif - -int main(void) -{ - DEFINE(__THREAD_info, offsetof(struct task_struct, stack)); - DEFINE(__THREAD_ksp, offsetof(struct task_struct, thread.ksp)); - DEFINE(__THREAD_mm_segment, offsetof(struct task_struct, thread.mm_segment)); - BLANK(); - DEFINE(__TASK_pid, offsetof(struct task_struct, pid)); - BLANK(); - DEFINE(__THREAD_per_cause, offsetof(struct task_struct, thread.per_event.cause)); - DEFINE(__THREAD_per_address, offsetof(struct task_struct, thread.per_event.address)); - DEFINE(__THREAD_per_paid, offsetof(struct task_struct, thread.per_event.paid)); - BLANK(); - DEFINE(__TI_task, offsetof(struct thread_info, task)); - DEFINE(__TI_domain, offsetof(struct thread_info, exec_domain)); - DEFINE(__TI_flags, offsetof(struct thread_info, flags)); - DEFINE(__TI_cpu, offsetof(struct thread_info, cpu)); - DEFINE(__TI_precount, offsetof(struct thread_info, preempt_count)); - DEFINE(__TI_user_timer, offsetof(struct thread_info, user_timer)); - DEFINE(__TI_system_timer, offsetof(struct thread_info, system_timer)); - DEFINE(__TI_last_break, offsetof(struct thread_info, last_break)); - BLANK(); - DEFINE(__PT_ARGS, offsetof(struct pt_regs, args)); - DEFINE(__PT_PSW, offsetof(struct pt_regs, psw)); - DEFINE(__PT_GPRS, offsetof(struct pt_regs, gprs)); - DEFINE(__PT_ORIG_GPR2, offsetof(struct pt_regs, orig_gpr2)); - DEFINE(__PT_INT_CODE, offsetof(struct pt_regs, int_code)); - DEFINE(__PT_INT_PARM_LONG, offsetof(struct pt_regs, int_parm_long)); - DEFINE(__PT_SIZE, sizeof(struct pt_regs)); - BLANK(); - DEFINE(__SF_BACKCHAIN, offsetof(struct stack_frame, back_chain)); - DEFINE(__SF_GPRS, offsetof(struct stack_frame, gprs)); - DEFINE(__SF_EMPTY, offsetof(struct stack_frame, empty1)); - BLANK(); - /* timeval/timezone offsets for use by vdso */ - DEFINE(__VDSO_UPD_COUNT, offsetof(struct vdso_data, tb_update_count)); - DEFINE(__VDSO_XTIME_STAMP, offsetof(struct vdso_data, xtime_tod_stamp)); - DEFINE(__VDSO_XTIME_SEC, offsetof(struct vdso_data, xtime_clock_sec)); - DEFINE(__VDSO_XTIME_NSEC, offsetof(struct vdso_data, xtime_clock_nsec)); - DEFINE(__VDSO_WTOM_SEC, offsetof(struct vdso_data, wtom_clock_sec)); - DEFINE(__VDSO_WTOM_NSEC, offsetof(struct vdso_data, wtom_clock_nsec)); - DEFINE(__VDSO_TIMEZONE, offsetof(struct vdso_data, tz_minuteswest)); - DEFINE(__VDSO_ECTG_OK, offsetof(struct vdso_data, ectg_available)); - DEFINE(__VDSO_NTP_MULT, offsetof(struct vdso_data, ntp_mult)); - DEFINE(__VDSO_ECTG_BASE, offsetof(struct vdso_per_cpu_data, ectg_timer_base)); - DEFINE(__VDSO_ECTG_USER, offsetof(struct vdso_per_cpu_data, ectg_user_time)); - /* constants used by the vdso */ - DEFINE(__CLOCK_REALTIME, CLOCK_REALTIME); - DEFINE(__CLOCK_MONOTONIC, CLOCK_MONOTONIC); - DEFINE(__CLOCK_REALTIME_RES, MONOTONIC_RES_NSEC); - BLANK(); - /* idle data offsets */ - DEFINE(__IDLE_ENTER, offsetof(struct s390_idle_data, idle_enter)); - DEFINE(__IDLE_EXIT, offsetof(struct s390_idle_data, idle_exit)); - /* vtimer queue offsets */ - DEFINE(__VQ_IDLE_ENTER, offsetof(struct vtimer_queue, idle_enter)); - DEFINE(__VQ_IDLE_EXIT, offsetof(struct vtimer_queue, idle_exit)); - /* lowcore offsets */ - DEFINE(__LC_EXT_PARAMS, offsetof(struct _lowcore, ext_params)); - DEFINE(__LC_EXT_CPU_ADDR, offsetof(struct _lowcore, ext_cpu_addr)); - DEFINE(__LC_EXT_INT_CODE, offsetof(struct _lowcore, ext_int_code)); - DEFINE(__LC_SVC_ILC, offsetof(struct _lowcore, svc_ilc)); - DEFINE(__LC_SVC_INT_CODE, offsetof(struct _lowcore, svc_code)); - DEFINE(__LC_PGM_ILC, offsetof(struct _lowcore, pgm_ilc)); - DEFINE(__LC_PGM_INT_CODE, offsetof(struct _lowcore, pgm_code)); - DEFINE(__LC_TRANS_EXC_CODE, offsetof(struct _lowcore, trans_exc_code)); - DEFINE(__LC_PER_CAUSE, offsetof(struct _lowcore, per_perc_atmid)); - DEFINE(__LC_PER_ADDRESS, offsetof(struct _lowcore, per_address)); - DEFINE(__LC_PER_PAID, offsetof(struct _lowcore, per_access_id)); - DEFINE(__LC_AR_MODE_ID, offsetof(struct _lowcore, ar_access_id)); - DEFINE(__LC_SUBCHANNEL_ID, offsetof(struct _lowcore, subchannel_id)); - DEFINE(__LC_SUBCHANNEL_NR, offsetof(struct _lowcore, subchannel_nr)); - DEFINE(__LC_IO_INT_PARM, offsetof(struct _lowcore, io_int_parm)); - DEFINE(__LC_IO_INT_WORD, offsetof(struct _lowcore, io_int_word)); - DEFINE(__LC_STFL_FAC_LIST, offsetof(struct _lowcore, stfl_fac_list)); - DEFINE(__LC_MCCK_CODE, offsetof(struct _lowcore, mcck_interruption_code)); - DEFINE(__LC_RST_OLD_PSW, offsetof(struct _lowcore, restart_old_psw)); - DEFINE(__LC_EXT_OLD_PSW, offsetof(struct _lowcore, external_old_psw)); - DEFINE(__LC_SVC_OLD_PSW, offsetof(struct _lowcore, svc_old_psw)); - DEFINE(__LC_PGM_OLD_PSW, offsetof(struct _lowcore, program_old_psw)); - DEFINE(__LC_MCK_OLD_PSW, offsetof(struct _lowcore, mcck_old_psw)); - DEFINE(__LC_IO_OLD_PSW, offsetof(struct _lowcore, io_old_psw)); - DEFINE(__LC_RST_NEW_PSW, offsetof(struct _lowcore, restart_psw)); - DEFINE(__LC_EXT_NEW_PSW, offsetof(struct _lowcore, external_new_psw)); - DEFINE(__LC_SVC_NEW_PSW, offsetof(struct _lowcore, svc_new_psw)); - DEFINE(__LC_PGM_NEW_PSW, offsetof(struct _lowcore, program_new_psw)); - DEFINE(__LC_MCK_NEW_PSW, offsetof(struct _lowcore, mcck_new_psw)); - DEFINE(__LC_IO_NEW_PSW, offsetof(struct _lowcore, io_new_psw)); - BLANK(); - DEFINE(__LC_SAVE_AREA_SYNC, offsetof(struct _lowcore, save_area_sync)); - DEFINE(__LC_SAVE_AREA_ASYNC, offsetof(struct _lowcore, save_area_async)); - DEFINE(__LC_SAVE_AREA_RESTART, offsetof(struct _lowcore, save_area_restart)); - DEFINE(__LC_RETURN_PSW, offsetof(struct _lowcore, return_psw)); - DEFINE(__LC_RETURN_MCCK_PSW, offsetof(struct _lowcore, return_mcck_psw)); - DEFINE(__LC_SYNC_ENTER_TIMER, offsetof(struct _lowcore, sync_enter_timer)); - DEFINE(__LC_ASYNC_ENTER_TIMER, offsetof(struct _lowcore, async_enter_timer)); - DEFINE(__LC_MCCK_ENTER_TIMER, offsetof(struct _lowcore, mcck_enter_timer)); - DEFINE(__LC_EXIT_TIMER, offsetof(struct _lowcore, exit_timer)); - DEFINE(__LC_USER_TIMER, offsetof(struct _lowcore, user_timer)); - DEFINE(__LC_SYSTEM_TIMER, offsetof(struct _lowcore, system_timer)); - DEFINE(__LC_STEAL_TIMER, offsetof(struct _lowcore, steal_timer)); - DEFINE(__LC_LAST_UPDATE_TIMER, offsetof(struct _lowcore, last_update_timer)); - DEFINE(__LC_LAST_UPDATE_CLOCK, offsetof(struct _lowcore, last_update_clock)); - DEFINE(__LC_CURRENT, offsetof(struct _lowcore, current_task)); - DEFINE(__LC_CURRENT_PID, offsetof(struct _lowcore, current_pid)); - DEFINE(__LC_THREAD_INFO, offsetof(struct _lowcore, thread_info)); - DEFINE(__LC_KERNEL_STACK, offsetof(struct _lowcore, kernel_stack)); - DEFINE(__LC_ASYNC_STACK, offsetof(struct _lowcore, async_stack)); - DEFINE(__LC_PANIC_STACK, offsetof(struct _lowcore, panic_stack)); - DEFINE(__LC_RESTART_STACK, offsetof(struct _lowcore, restart_stack)); - DEFINE(__LC_RESTART_FN, offsetof(struct _lowcore, restart_fn)); - DEFINE(__LC_USER_ASCE, offsetof(struct _lowcore, user_asce)); - DEFINE(__LC_INT_CLOCK, offsetof(struct _lowcore, int_clock)); - DEFINE(__LC_MCCK_CLOCK, offsetof(struct _lowcore, mcck_clock)); - DEFINE(__LC_MACHINE_FLAGS, offsetof(struct _lowcore, machine_flags)); - DEFINE(__LC_FTRACE_FUNC, offsetof(struct _lowcore, ftrace_func)); - DEFINE(__LC_IRB, offsetof(struct _lowcore, irb)); - DEFINE(__LC_DUMP_REIPL, offsetof(struct _lowcore, ipib)); - BLANK(); - DEFINE(__LC_CPU_TIMER_SAVE_AREA, offsetof(struct _lowcore, cpu_timer_save_area)); - DEFINE(__LC_CLOCK_COMP_SAVE_AREA, offsetof(struct _lowcore, clock_comp_save_area)); - DEFINE(__LC_PSW_SAVE_AREA, offsetof(struct _lowcore, psw_save_area)); - DEFINE(__LC_PREFIX_SAVE_AREA, offsetof(struct _lowcore, prefixreg_save_area)); - DEFINE(__LC_AREGS_SAVE_AREA, offsetof(struct _lowcore, access_regs_save_area)); - DEFINE(__LC_FPREGS_SAVE_AREA, offsetof(struct _lowcore, floating_pt_save_area)); - DEFINE(__LC_GPREGS_SAVE_AREA, offsetof(struct _lowcore, gpregs_save_area)); - DEFINE(__LC_CREGS_SAVE_AREA, offsetof(struct _lowcore, cregs_save_area)); -#ifdef CONFIG_32BIT - DEFINE(SAVE_AREA_BASE, offsetof(struct _lowcore, extended_save_area_addr)); -#else /* CONFIG_32BIT */ - DEFINE(__LC_EXT_PARAMS2, offsetof(struct _lowcore, ext_params2)); - DEFINE(SAVE_AREA_BASE, offsetof(struct _lowcore, floating_pt_save_area)); - DEFINE(__LC_PASTE, offsetof(struct _lowcore, paste)); - DEFINE(__LC_FP_CREG_SAVE_AREA, offsetof(struct _lowcore, fpt_creg_save_area)); - DEFINE(__LC_LAST_BREAK, offsetof(struct _lowcore, breaking_event_addr)); - DEFINE(__LC_VDSO_PER_CPU, offsetof(struct _lowcore, vdso_per_cpu_data)); - DEFINE(__LC_GMAP, offsetof(struct _lowcore, gmap)); - DEFINE(__GMAP_ASCE, offsetof(struct gmap, asce)); -#endif /* CONFIG_32BIT */ - return 0; -} diff --git a/ANDROID_3.4.5/arch/s390/kernel/audit.c b/ANDROID_3.4.5/arch/s390/kernel/audit.c deleted file mode 100644 index f4932c22..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/audit.c +++ /dev/null @@ -1,78 +0,0 @@ -#include <linux/init.h> -#include <linux/types.h> -#include <linux/audit.h> -#include <asm/unistd.h> -#include "audit.h" - -static unsigned dir_class[] = { -#include <asm-generic/audit_dir_write.h> -~0U -}; - -static unsigned read_class[] = { -#include <asm-generic/audit_read.h> -~0U -}; - -static unsigned write_class[] = { -#include <asm-generic/audit_write.h> -~0U -}; - -static unsigned chattr_class[] = { -#include <asm-generic/audit_change_attr.h> -~0U -}; - -static unsigned signal_class[] = { -#include <asm-generic/audit_signal.h> -~0U -}; - -int audit_classify_arch(int arch) -{ -#ifdef CONFIG_COMPAT - if (arch == AUDIT_ARCH_S390) - return 1; -#endif - return 0; -} - -int audit_classify_syscall(int abi, unsigned syscall) -{ -#ifdef CONFIG_COMPAT - if (abi == AUDIT_ARCH_S390) - return s390_classify_syscall(syscall); -#endif - switch(syscall) { - case __NR_open: - return 2; - case __NR_openat: - return 3; - case __NR_socketcall: - return 4; - case __NR_execve: - return 5; - default: - return 0; - } -} - -static int __init audit_classes_init(void) -{ -#ifdef CONFIG_COMPAT - audit_register_class(AUDIT_CLASS_WRITE_32, s390_write_class); - audit_register_class(AUDIT_CLASS_READ_32, s390_read_class); - audit_register_class(AUDIT_CLASS_DIR_WRITE_32, s390_dir_class); - audit_register_class(AUDIT_CLASS_CHATTR_32, s390_chattr_class); - audit_register_class(AUDIT_CLASS_SIGNAL_32, s390_signal_class); -#endif - audit_register_class(AUDIT_CLASS_WRITE, write_class); - audit_register_class(AUDIT_CLASS_READ, read_class); - audit_register_class(AUDIT_CLASS_DIR_WRITE, dir_class); - audit_register_class(AUDIT_CLASS_CHATTR, chattr_class); - audit_register_class(AUDIT_CLASS_SIGNAL, signal_class); - return 0; -} - -__initcall(audit_classes_init); diff --git a/ANDROID_3.4.5/arch/s390/kernel/audit.h b/ANDROID_3.4.5/arch/s390/kernel/audit.h deleted file mode 100644 index 12b56f4b..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/audit.h +++ /dev/null @@ -1,15 +0,0 @@ -#ifndef __ARCH_S390_KERNEL_AUDIT_H -#define __ARCH_S390_KERNEL_AUDIT_H - -#include <linux/types.h> - -#ifdef CONFIG_COMPAT -extern int s390_classify_syscall(unsigned); -extern __u32 s390_dir_class[]; -extern __u32 s390_write_class[]; -extern __u32 s390_read_class[]; -extern __u32 s390_chattr_class[]; -extern __u32 s390_signal_class[]; -#endif /* CONFIG_COMPAT */ - -#endif /* __ARCH_S390_KERNEL_AUDIT_H */ diff --git a/ANDROID_3.4.5/arch/s390/kernel/base.S b/ANDROID_3.4.5/arch/s390/kernel/base.S deleted file mode 100644 index 3aa4d00a..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/base.S +++ /dev/null @@ -1,193 +0,0 @@ -/* - * arch/s390/kernel/base.S - * - * Copyright IBM Corp. 2006,2007 - * Author(s): Heiko Carstens <heiko.carstens@de.ibm.com> - * Michael Holzheu <holzheu@de.ibm.com> - */ - -#include <linux/linkage.h> -#include <asm/asm-offsets.h> -#include <asm/ptrace.h> - -#ifdef CONFIG_64BIT - -ENTRY(s390_base_mcck_handler) - basr %r13,0 -0: lg %r15,__LC_PANIC_STACK # load panic stack - aghi %r15,-STACK_FRAME_OVERHEAD - larl %r1,s390_base_mcck_handler_fn - lg %r1,0(%r1) - ltgr %r1,%r1 - jz 1f - basr %r14,%r1 -1: la %r1,4095 - lmg %r0,%r15,__LC_GPREGS_SAVE_AREA-4095(%r1) - lpswe __LC_MCK_OLD_PSW - - .section .bss - .align 8 - .globl s390_base_mcck_handler_fn -s390_base_mcck_handler_fn: - .quad 0 - .previous - -ENTRY(s390_base_ext_handler) - stmg %r0,%r15,__LC_SAVE_AREA_ASYNC - basr %r13,0 -0: aghi %r15,-STACK_FRAME_OVERHEAD - larl %r1,s390_base_ext_handler_fn - lg %r1,0(%r1) - ltgr %r1,%r1 - jz 1f - basr %r14,%r1 -1: lmg %r0,%r15,__LC_SAVE_AREA_ASYNC - ni __LC_EXT_OLD_PSW+1,0xfd # clear wait state bit - lpswe __LC_EXT_OLD_PSW - - .section .bss - .align 8 - .globl s390_base_ext_handler_fn -s390_base_ext_handler_fn: - .quad 0 - .previous - -ENTRY(s390_base_pgm_handler) - stmg %r0,%r15,__LC_SAVE_AREA_SYNC - basr %r13,0 -0: aghi %r15,-STACK_FRAME_OVERHEAD - larl %r1,s390_base_pgm_handler_fn - lg %r1,0(%r1) - ltgr %r1,%r1 - jz 1f - basr %r14,%r1 - lmg %r0,%r15,__LC_SAVE_AREA_SYNC - lpswe __LC_PGM_OLD_PSW -1: lpswe disabled_wait_psw-0b(%r13) - - .align 8 -disabled_wait_psw: - .quad 0x0002000180000000,0x0000000000000000 + s390_base_pgm_handler - - .section .bss - .align 8 - .globl s390_base_pgm_handler_fn -s390_base_pgm_handler_fn: - .quad 0 - .previous - -# -# Calls diag 308 subcode 1 and continues execution -# -# The following conditions must be ensured before calling this function: -# * Prefix register = 0 -# * Lowcore protection is disabled -# -ENTRY(diag308_reset) - larl %r4,.Lctlregs # Save control registers - stctg %c0,%c15,0(%r4) - larl %r4,.Lfpctl # Floating point control register - stfpc 0(%r4) - larl %r4,.Lrestart_psw # Setup restart PSW at absolute 0 - lghi %r3,0 - lg %r4,0(%r4) # Save PSW - sturg %r4,%r3 # Use sturg, because of large pages - lghi %r1,1 - diag %r1,%r1,0x308 -.Lrestart_part2: - lhi %r0,0 # Load r0 with zero - lhi %r1,2 # Use mode 2 = ESAME (dump) - sigp %r1,%r0,0x12 # Switch to ESAME mode - sam64 # Switch to 64 bit addressing mode - larl %r4,.Lctlregs # Restore control registers - lctlg %c0,%c15,0(%r4) - larl %r4,.Lfpctl # Restore floating point ctl register - lfpc 0(%r4) - br %r14 -.align 16 -.Lrestart_psw: - .long 0x00080000,0x80000000 + .Lrestart_part2 - - .section .bss -.align 8 -.Lctlregs: - .rept 16 - .quad 0 - .endr -.Lfpctl: - .long 0 - .previous - -#else /* CONFIG_64BIT */ - -ENTRY(s390_base_mcck_handler) - basr %r13,0 -0: l %r15,__LC_PANIC_STACK # load panic stack - ahi %r15,-STACK_FRAME_OVERHEAD - l %r1,2f-0b(%r13) - l %r1,0(%r1) - ltr %r1,%r1 - jz 1f - basr %r14,%r1 -1: lm %r0,%r15,__LC_GPREGS_SAVE_AREA - lpsw __LC_MCK_OLD_PSW - -2: .long s390_base_mcck_handler_fn - - .section .bss - .align 4 - .globl s390_base_mcck_handler_fn -s390_base_mcck_handler_fn: - .long 0 - .previous - -ENTRY(s390_base_ext_handler) - stm %r0,%r15,__LC_SAVE_AREA_ASYNC - basr %r13,0 -0: ahi %r15,-STACK_FRAME_OVERHEAD - l %r1,2f-0b(%r13) - l %r1,0(%r1) - ltr %r1,%r1 - jz 1f - basr %r14,%r1 -1: lm %r0,%r15,__LC_SAVE_AREA_ASYNC - ni __LC_EXT_OLD_PSW+1,0xfd # clear wait state bit - lpsw __LC_EXT_OLD_PSW - -2: .long s390_base_ext_handler_fn - - .section .bss - .align 4 - .globl s390_base_ext_handler_fn -s390_base_ext_handler_fn: - .long 0 - .previous - -ENTRY(s390_base_pgm_handler) - stm %r0,%r15,__LC_SAVE_AREA_SYNC - basr %r13,0 -0: ahi %r15,-STACK_FRAME_OVERHEAD - l %r1,2f-0b(%r13) - l %r1,0(%r1) - ltr %r1,%r1 - jz 1f - basr %r14,%r1 - lm %r0,%r15,__LC_SAVE_AREA_SYNC - lpsw __LC_PGM_OLD_PSW - -1: lpsw disabled_wait_psw-0b(%r13) - -2: .long s390_base_pgm_handler_fn - -disabled_wait_psw: - .align 8 - .long 0x000a0000,0x00000000 + s390_base_pgm_handler - - .section .bss - .align 4 - .globl s390_base_pgm_handler_fn -s390_base_pgm_handler_fn: - .long 0 - .previous - -#endif /* CONFIG_64BIT */ diff --git a/ANDROID_3.4.5/arch/s390/kernel/bitmap.c b/ANDROID_3.4.5/arch/s390/kernel/bitmap.c deleted file mode 100644 index 3ae4757b..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/bitmap.c +++ /dev/null @@ -1,54 +0,0 @@ -/* - * Bitmaps for set_bit, clear_bit, test_and_set_bit, ... - * See include/asm/{bitops.h|posix_types.h} for details - * - * Copyright IBM Corp. 1999,2009 - * Author(s): Martin Schwidefsky <schwidefsky@de.ibm.com>, - */ - -#include <linux/bitops.h> -#include <linux/module.h> - -const char _oi_bitmap[] = { 0x01, 0x02, 0x04, 0x08, 0x10, 0x20, 0x40, 0x80 }; -EXPORT_SYMBOL(_oi_bitmap); - -const char _ni_bitmap[] = { 0xfe, 0xfd, 0xfb, 0xf7, 0xef, 0xdf, 0xbf, 0x7f }; -EXPORT_SYMBOL(_ni_bitmap); - -const char _zb_findmap[] = { - 0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,4, - 0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,5, - 0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,4, - 0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,6, - 0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,4, - 0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,5, - 0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,4, - 0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,7, - 0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,4, - 0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,5, - 0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,4, - 0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,6, - 0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,4, - 0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,5, - 0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,4, - 0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,8 }; -EXPORT_SYMBOL(_zb_findmap); - -const char _sb_findmap[] = { - 8,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0, - 4,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0, - 5,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0, - 4,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0, - 6,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0, - 4,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0, - 5,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0, - 4,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0, - 7,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0, - 4,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0, - 5,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0, - 4,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0, - 6,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0, - 4,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0, - 5,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0, - 4,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0 }; -EXPORT_SYMBOL(_sb_findmap); diff --git a/ANDROID_3.4.5/arch/s390/kernel/compat_audit.c b/ANDROID_3.4.5/arch/s390/kernel/compat_audit.c deleted file mode 100644 index d6487bf8..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/compat_audit.c +++ /dev/null @@ -1,44 +0,0 @@ -#undef __s390x__ -#include <asm/unistd.h> -#include "audit.h" - -unsigned s390_dir_class[] = { -#include <asm-generic/audit_dir_write.h> -~0U -}; - -unsigned s390_chattr_class[] = { -#include <asm-generic/audit_change_attr.h> -~0U -}; - -unsigned s390_write_class[] = { -#include <asm-generic/audit_write.h> -~0U -}; - -unsigned s390_read_class[] = { -#include <asm-generic/audit_read.h> -~0U -}; - -unsigned s390_signal_class[] = { -#include <asm-generic/audit_signal.h> -~0U -}; - -int s390_classify_syscall(unsigned syscall) -{ - switch(syscall) { - case __NR_open: - return 2; - case __NR_openat: - return 3; - case __NR_socketcall: - return 4; - case __NR_execve: - return 5; - default: - return 1; - } -} diff --git a/ANDROID_3.4.5/arch/s390/kernel/compat_exec_domain.c b/ANDROID_3.4.5/arch/s390/kernel/compat_exec_domain.c deleted file mode 100644 index 914d4944..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/compat_exec_domain.c +++ /dev/null @@ -1,29 +0,0 @@ -/* - * Support for 32-bit Linux for S390 personality. - * - * Copyright (C) 2000 IBM Deutschland Entwicklung GmbH, IBM Corporation - * Author(s): Gerhard Tonn (ton@de.ibm.com) - * - * - */ - -#include <linux/kernel.h> -#include <linux/init.h> -#include <linux/personality.h> -#include <linux/sched.h> - -static struct exec_domain s390_exec_domain; - -static int __init s390_init (void) -{ - s390_exec_domain.name = "Linux/s390"; - s390_exec_domain.handler = NULL; - s390_exec_domain.pers_low = PER_LINUX32; - s390_exec_domain.pers_high = PER_LINUX32; - s390_exec_domain.signal_map = default_exec_domain.signal_map; - s390_exec_domain.signal_invmap = default_exec_domain.signal_invmap; - register_exec_domain(&s390_exec_domain); - return 0; -} - -__initcall(s390_init); diff --git a/ANDROID_3.4.5/arch/s390/kernel/compat_linux.c b/ANDROID_3.4.5/arch/s390/kernel/compat_linux.c deleted file mode 100644 index ab64bdba..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/compat_linux.c +++ /dev/null @@ -1,681 +0,0 @@ -/* - * arch/s390x/kernel/linux32.c - * - * S390 version - * Copyright (C) 2000 IBM Deutschland Entwicklung GmbH, IBM Corporation - * Author(s): Martin Schwidefsky (schwidefsky@de.ibm.com), - * Gerhard Tonn (ton@de.ibm.com) - * Thomas Spatzier (tspat@de.ibm.com) - * - * Conversion between 31bit and 64bit native syscalls. - * - * Heavily inspired by the 32-bit Sparc compat code which is - * Copyright (C) 1997,1998 Jakub Jelinek (jj@sunsite.mff.cuni.cz) - * Copyright (C) 1997 David S. Miller (davem@caip.rutgers.edu) - * - */ - - -#include <linux/kernel.h> -#include <linux/sched.h> -#include <linux/fs.h> -#include <linux/mm.h> -#include <linux/file.h> -#include <linux/signal.h> -#include <linux/resource.h> -#include <linux/times.h> -#include <linux/smp.h> -#include <linux/sem.h> -#include <linux/msg.h> -#include <linux/shm.h> -#include <linux/uio.h> -#include <linux/quota.h> -#include <linux/module.h> -#include <linux/poll.h> -#include <linux/personality.h> -#include <linux/stat.h> -#include <linux/filter.h> -#include <linux/highmem.h> -#include <linux/highuid.h> -#include <linux/mman.h> -#include <linux/ipv6.h> -#include <linux/in.h> -#include <linux/icmpv6.h> -#include <linux/syscalls.h> -#include <linux/sysctl.h> -#include <linux/binfmts.h> -#include <linux/capability.h> -#include <linux/compat.h> -#include <linux/vfs.h> -#include <linux/ptrace.h> -#include <linux/fadvise.h> -#include <linux/ipc.h> -#include <linux/slab.h> - -#include <asm/types.h> -#include <asm/uaccess.h> - -#include <net/scm.h> -#include <net/sock.h> - -#include "compat_linux.h" - -u32 psw32_user_bits = PSW32_MASK_DAT | PSW32_MASK_IO | PSW32_MASK_EXT | - PSW32_DEFAULT_KEY | PSW32_MASK_BASE | PSW32_MASK_MCHECK | - PSW32_MASK_PSTATE | PSW32_ASC_HOME; - -/* For this source file, we want overflow handling. */ - -#undef high2lowuid -#undef high2lowgid -#undef low2highuid -#undef low2highgid -#undef SET_UID16 -#undef SET_GID16 -#undef NEW_TO_OLD_UID -#undef NEW_TO_OLD_GID -#undef SET_OLDSTAT_UID -#undef SET_OLDSTAT_GID -#undef SET_STAT_UID -#undef SET_STAT_GID - -#define high2lowuid(uid) ((uid) > 65535) ? (u16)overflowuid : (u16)(uid) -#define high2lowgid(gid) ((gid) > 65535) ? (u16)overflowgid : (u16)(gid) -#define low2highuid(uid) ((uid) == (u16)-1) ? (uid_t)-1 : (uid_t)(uid) -#define low2highgid(gid) ((gid) == (u16)-1) ? (gid_t)-1 : (gid_t)(gid) -#define SET_UID16(var, uid) var = high2lowuid(uid) -#define SET_GID16(var, gid) var = high2lowgid(gid) -#define NEW_TO_OLD_UID(uid) high2lowuid(uid) -#define NEW_TO_OLD_GID(gid) high2lowgid(gid) -#define SET_OLDSTAT_UID(stat, uid) (stat).st_uid = high2lowuid(uid) -#define SET_OLDSTAT_GID(stat, gid) (stat).st_gid = high2lowgid(gid) -#define SET_STAT_UID(stat, uid) (stat).st_uid = high2lowuid(uid) -#define SET_STAT_GID(stat, gid) (stat).st_gid = high2lowgid(gid) - -asmlinkage long sys32_chown16(const char __user * filename, u16 user, u16 group) -{ - return sys_chown(filename, low2highuid(user), low2highgid(group)); -} - -asmlinkage long sys32_lchown16(const char __user * filename, u16 user, u16 group) -{ - return sys_lchown(filename, low2highuid(user), low2highgid(group)); -} - -asmlinkage long sys32_fchown16(unsigned int fd, u16 user, u16 group) -{ - return sys_fchown(fd, low2highuid(user), low2highgid(group)); -} - -asmlinkage long sys32_setregid16(u16 rgid, u16 egid) -{ - return sys_setregid(low2highgid(rgid), low2highgid(egid)); -} - -asmlinkage long sys32_setgid16(u16 gid) -{ - return sys_setgid((gid_t)gid); -} - -asmlinkage long sys32_setreuid16(u16 ruid, u16 euid) -{ - return sys_setreuid(low2highuid(ruid), low2highuid(euid)); -} - -asmlinkage long sys32_setuid16(u16 uid) -{ - return sys_setuid((uid_t)uid); -} - -asmlinkage long sys32_setresuid16(u16 ruid, u16 euid, u16 suid) -{ - return sys_setresuid(low2highuid(ruid), low2highuid(euid), - low2highuid(suid)); -} - -asmlinkage long sys32_getresuid16(u16 __user *ruid, u16 __user *euid, u16 __user *suid) -{ - int retval; - - if (!(retval = put_user(high2lowuid(current->cred->uid), ruid)) && - !(retval = put_user(high2lowuid(current->cred->euid), euid))) - retval = put_user(high2lowuid(current->cred->suid), suid); - - return retval; -} - -asmlinkage long sys32_setresgid16(u16 rgid, u16 egid, u16 sgid) -{ - return sys_setresgid(low2highgid(rgid), low2highgid(egid), - low2highgid(sgid)); -} - -asmlinkage long sys32_getresgid16(u16 __user *rgid, u16 __user *egid, u16 __user *sgid) -{ - int retval; - - if (!(retval = put_user(high2lowgid(current->cred->gid), rgid)) && - !(retval = put_user(high2lowgid(current->cred->egid), egid))) - retval = put_user(high2lowgid(current->cred->sgid), sgid); - - return retval; -} - -asmlinkage long sys32_setfsuid16(u16 uid) -{ - return sys_setfsuid((uid_t)uid); -} - -asmlinkage long sys32_setfsgid16(u16 gid) -{ - return sys_setfsgid((gid_t)gid); -} - -static int groups16_to_user(u16 __user *grouplist, struct group_info *group_info) -{ - int i; - u16 group; - - for (i = 0; i < group_info->ngroups; i++) { - group = (u16)GROUP_AT(group_info, i); - if (put_user(group, grouplist+i)) - return -EFAULT; - } - - return 0; -} - -static int groups16_from_user(struct group_info *group_info, u16 __user *grouplist) -{ - int i; - u16 group; - - for (i = 0; i < group_info->ngroups; i++) { - if (get_user(group, grouplist+i)) - return -EFAULT; - GROUP_AT(group_info, i) = (gid_t)group; - } - - return 0; -} - -asmlinkage long sys32_getgroups16(int gidsetsize, u16 __user *grouplist) -{ - int i; - - if (gidsetsize < 0) - return -EINVAL; - - get_group_info(current->cred->group_info); - i = current->cred->group_info->ngroups; - if (gidsetsize) { - if (i > gidsetsize) { - i = -EINVAL; - goto out; - } - if (groups16_to_user(grouplist, current->cred->group_info)) { - i = -EFAULT; - goto out; - } - } -out: - put_group_info(current->cred->group_info); - return i; -} - -asmlinkage long sys32_setgroups16(int gidsetsize, u16 __user *grouplist) -{ - struct group_info *group_info; - int retval; - - if (!capable(CAP_SETGID)) - return -EPERM; - if ((unsigned)gidsetsize > NGROUPS_MAX) - return -EINVAL; - - group_info = groups_alloc(gidsetsize); - if (!group_info) - return -ENOMEM; - retval = groups16_from_user(group_info, grouplist); - if (retval) { - put_group_info(group_info); - return retval; - } - - retval = set_current_groups(group_info); - put_group_info(group_info); - - return retval; -} - -asmlinkage long sys32_getuid16(void) -{ - return high2lowuid(current->cred->uid); -} - -asmlinkage long sys32_geteuid16(void) -{ - return high2lowuid(current->cred->euid); -} - -asmlinkage long sys32_getgid16(void) -{ - return high2lowgid(current->cred->gid); -} - -asmlinkage long sys32_getegid16(void) -{ - return high2lowgid(current->cred->egid); -} - -/* - * sys32_ipc() is the de-multiplexer for the SysV IPC calls in 32bit emulation. - * - * This is really horribly ugly. - */ -#ifdef CONFIG_SYSVIPC -asmlinkage long sys32_ipc(u32 call, int first, int second, int third, u32 ptr) -{ - if (call >> 16) /* hack for backward compatibility */ - return -EINVAL; - switch (call) { - case SEMTIMEDOP: - return compat_sys_semtimedop(first, compat_ptr(ptr), - second, compat_ptr(third)); - case SEMOP: - /* struct sembuf is the same on 32 and 64bit :)) */ - return sys_semtimedop(first, compat_ptr(ptr), - second, NULL); - case SEMGET: - return sys_semget(first, second, third); - case SEMCTL: - return compat_sys_semctl(first, second, third, - compat_ptr(ptr)); - case MSGSND: - return compat_sys_msgsnd(first, second, third, - compat_ptr(ptr)); - case MSGRCV: - return compat_sys_msgrcv(first, second, 0, third, - 0, compat_ptr(ptr)); - case MSGGET: - return sys_msgget((key_t) first, second); - case MSGCTL: - return compat_sys_msgctl(first, second, compat_ptr(ptr)); - case SHMAT: - return compat_sys_shmat(first, second, third, - 0, compat_ptr(ptr)); - case SHMDT: - return sys_shmdt(compat_ptr(ptr)); - case SHMGET: - return sys_shmget(first, (unsigned)second, third); - case SHMCTL: - return compat_sys_shmctl(first, second, compat_ptr(ptr)); - } - - return -ENOSYS; -} -#endif - -asmlinkage long sys32_truncate64(const char __user * path, unsigned long high, unsigned long low) -{ - if ((int)high < 0) - return -EINVAL; - else - return sys_truncate(path, (high << 32) | low); -} - -asmlinkage long sys32_ftruncate64(unsigned int fd, unsigned long high, unsigned long low) -{ - if ((int)high < 0) - return -EINVAL; - else - return sys_ftruncate(fd, (high << 32) | low); -} - -asmlinkage long sys32_sched_rr_get_interval(compat_pid_t pid, - struct compat_timespec __user *interval) -{ - struct timespec t; - int ret; - mm_segment_t old_fs = get_fs (); - - set_fs (KERNEL_DS); - ret = sys_sched_rr_get_interval(pid, - (struct timespec __force __user *) &t); - set_fs (old_fs); - if (put_compat_timespec(&t, interval)) - return -EFAULT; - return ret; -} - -asmlinkage long sys32_rt_sigprocmask(int how, compat_sigset_t __user *set, - compat_sigset_t __user *oset, size_t sigsetsize) -{ - sigset_t s; - compat_sigset_t s32; - int ret; - mm_segment_t old_fs = get_fs(); - - if (set) { - if (copy_from_user (&s32, set, sizeof(compat_sigset_t))) - return -EFAULT; - s.sig[0] = s32.sig[0] | (((long)s32.sig[1]) << 32); - } - set_fs (KERNEL_DS); - ret = sys_rt_sigprocmask(how, - set ? (sigset_t __force __user *) &s : NULL, - oset ? (sigset_t __force __user *) &s : NULL, - sigsetsize); - set_fs (old_fs); - if (ret) return ret; - if (oset) { - s32.sig[1] = (s.sig[0] >> 32); - s32.sig[0] = s.sig[0]; - if (copy_to_user (oset, &s32, sizeof(compat_sigset_t))) - return -EFAULT; - } - return 0; -} - -asmlinkage long sys32_rt_sigpending(compat_sigset_t __user *set, - size_t sigsetsize) -{ - sigset_t s; - compat_sigset_t s32; - int ret; - mm_segment_t old_fs = get_fs(); - - set_fs (KERNEL_DS); - ret = sys_rt_sigpending((sigset_t __force __user *) &s, sigsetsize); - set_fs (old_fs); - if (!ret) { - s32.sig[1] = (s.sig[0] >> 32); - s32.sig[0] = s.sig[0]; - if (copy_to_user (set, &s32, sizeof(compat_sigset_t))) - return -EFAULT; - } - return ret; -} - -asmlinkage long -sys32_rt_sigqueueinfo(int pid, int sig, compat_siginfo_t __user *uinfo) -{ - siginfo_t info; - int ret; - mm_segment_t old_fs = get_fs(); - - if (copy_siginfo_from_user32(&info, uinfo)) - return -EFAULT; - set_fs (KERNEL_DS); - ret = sys_rt_sigqueueinfo(pid, sig, (siginfo_t __force __user *) &info); - set_fs (old_fs); - return ret; -} - -/* - * sys32_execve() executes a new program after the asm stub has set - * things up for us. This should basically do what I want it to. - */ -asmlinkage long sys32_execve(const char __user *name, compat_uptr_t __user *argv, - compat_uptr_t __user *envp) -{ - struct pt_regs *regs = task_pt_regs(current); - char *filename; - long rc; - - filename = getname(name); - rc = PTR_ERR(filename); - if (IS_ERR(filename)) - return rc; - rc = compat_do_execve(filename, argv, envp, regs); - if (rc) - goto out; - current->thread.fp_regs.fpc=0; - asm volatile("sfpc %0,0" : : "d" (0)); - rc = regs->gprs[2]; -out: - putname(filename); - return rc; -} - -asmlinkage long sys32_pread64(unsigned int fd, char __user *ubuf, - size_t count, u32 poshi, u32 poslo) -{ - if ((compat_ssize_t) count < 0) - return -EINVAL; - return sys_pread64(fd, ubuf, count, ((loff_t)AA(poshi) << 32) | AA(poslo)); -} - -asmlinkage long sys32_pwrite64(unsigned int fd, const char __user *ubuf, - size_t count, u32 poshi, u32 poslo) -{ - if ((compat_ssize_t) count < 0) - return -EINVAL; - return sys_pwrite64(fd, ubuf, count, ((loff_t)AA(poshi) << 32) | AA(poslo)); -} - -asmlinkage compat_ssize_t sys32_readahead(int fd, u32 offhi, u32 offlo, s32 count) -{ - return sys_readahead(fd, ((loff_t)AA(offhi) << 32) | AA(offlo), count); -} - -asmlinkage long sys32_sendfile(int out_fd, int in_fd, compat_off_t __user *offset, size_t count) -{ - mm_segment_t old_fs = get_fs(); - int ret; - off_t of; - - if (offset && get_user(of, offset)) - return -EFAULT; - - set_fs(KERNEL_DS); - ret = sys_sendfile(out_fd, in_fd, - offset ? (off_t __force __user *) &of : NULL, count); - set_fs(old_fs); - - if (offset && put_user(of, offset)) - return -EFAULT; - - return ret; -} - -asmlinkage long sys32_sendfile64(int out_fd, int in_fd, - compat_loff_t __user *offset, s32 count) -{ - mm_segment_t old_fs = get_fs(); - int ret; - loff_t lof; - - if (offset && get_user(lof, offset)) - return -EFAULT; - - set_fs(KERNEL_DS); - ret = sys_sendfile64(out_fd, in_fd, - offset ? (loff_t __force __user *) &lof : NULL, - count); - set_fs(old_fs); - - if (offset && put_user(lof, offset)) - return -EFAULT; - - return ret; -} - -struct stat64_emu31 { - unsigned long long st_dev; - unsigned int __pad1; -#define STAT64_HAS_BROKEN_ST_INO 1 - u32 __st_ino; - unsigned int st_mode; - unsigned int st_nlink; - u32 st_uid; - u32 st_gid; - unsigned long long st_rdev; - unsigned int __pad3; - long st_size; - u32 st_blksize; - unsigned char __pad4[4]; - u32 __pad5; /* future possible st_blocks high bits */ - u32 st_blocks; /* Number 512-byte blocks allocated. */ - u32 st_atime; - u32 __pad6; - u32 st_mtime; - u32 __pad7; - u32 st_ctime; - u32 __pad8; /* will be high 32 bits of ctime someday */ - unsigned long st_ino; -}; - -static int cp_stat64(struct stat64_emu31 __user *ubuf, struct kstat *stat) -{ - struct stat64_emu31 tmp; - - memset(&tmp, 0, sizeof(tmp)); - - tmp.st_dev = huge_encode_dev(stat->dev); - tmp.st_ino = stat->ino; - tmp.__st_ino = (u32)stat->ino; - tmp.st_mode = stat->mode; - tmp.st_nlink = (unsigned int)stat->nlink; - tmp.st_uid = stat->uid; - tmp.st_gid = stat->gid; - tmp.st_rdev = huge_encode_dev(stat->rdev); - tmp.st_size = stat->size; - tmp.st_blksize = (u32)stat->blksize; - tmp.st_blocks = (u32)stat->blocks; - tmp.st_atime = (u32)stat->atime.tv_sec; - tmp.st_mtime = (u32)stat->mtime.tv_sec; - tmp.st_ctime = (u32)stat->ctime.tv_sec; - - return copy_to_user(ubuf,&tmp,sizeof(tmp)) ? -EFAULT : 0; -} - -asmlinkage long sys32_stat64(const char __user * filename, struct stat64_emu31 __user * statbuf) -{ - struct kstat stat; - int ret = vfs_stat(filename, &stat); - if (!ret) - ret = cp_stat64(statbuf, &stat); - return ret; -} - -asmlinkage long sys32_lstat64(const char __user * filename, struct stat64_emu31 __user * statbuf) -{ - struct kstat stat; - int ret = vfs_lstat(filename, &stat); - if (!ret) - ret = cp_stat64(statbuf, &stat); - return ret; -} - -asmlinkage long sys32_fstat64(unsigned long fd, struct stat64_emu31 __user * statbuf) -{ - struct kstat stat; - int ret = vfs_fstat(fd, &stat); - if (!ret) - ret = cp_stat64(statbuf, &stat); - return ret; -} - -asmlinkage long sys32_fstatat64(unsigned int dfd, const char __user *filename, - struct stat64_emu31 __user* statbuf, int flag) -{ - struct kstat stat; - int error; - - error = vfs_fstatat(dfd, filename, &stat, flag); - if (error) - return error; - return cp_stat64(statbuf, &stat); -} - -/* - * Linux/i386 didn't use to be able to handle more than - * 4 system call parameters, so these system calls used a memory - * block for parameter passing.. - */ - -struct mmap_arg_struct_emu31 { - compat_ulong_t addr; - compat_ulong_t len; - compat_ulong_t prot; - compat_ulong_t flags; - compat_ulong_t fd; - compat_ulong_t offset; -}; - -asmlinkage unsigned long old32_mmap(struct mmap_arg_struct_emu31 __user *arg) -{ - struct mmap_arg_struct_emu31 a; - - if (copy_from_user(&a, arg, sizeof(a))) - return -EFAULT; - if (a.offset & ~PAGE_MASK) - return -EINVAL; - a.addr = (unsigned long) compat_ptr(a.addr); - return sys_mmap_pgoff(a.addr, a.len, a.prot, a.flags, a.fd, - a.offset >> PAGE_SHIFT); -} - -asmlinkage long sys32_mmap2(struct mmap_arg_struct_emu31 __user *arg) -{ - struct mmap_arg_struct_emu31 a; - - if (copy_from_user(&a, arg, sizeof(a))) - return -EFAULT; - a.addr = (unsigned long) compat_ptr(a.addr); - return sys_mmap_pgoff(a.addr, a.len, a.prot, a.flags, a.fd, a.offset); -} - -asmlinkage long sys32_read(unsigned int fd, char __user * buf, size_t count) -{ - if ((compat_ssize_t) count < 0) - return -EINVAL; - - return sys_read(fd, buf, count); -} - -asmlinkage long sys32_write(unsigned int fd, const char __user * buf, size_t count) -{ - if ((compat_ssize_t) count < 0) - return -EINVAL; - - return sys_write(fd, buf, count); -} - -/* - * 31 bit emulation wrapper functions for sys_fadvise64/fadvise64_64. - * These need to rewrite the advise values for POSIX_FADV_{DONTNEED,NOREUSE} - * because the 31 bit values differ from the 64 bit values. - */ - -asmlinkage long -sys32_fadvise64(int fd, loff_t offset, size_t len, int advise) -{ - if (advise == 4) - advise = POSIX_FADV_DONTNEED; - else if (advise == 5) - advise = POSIX_FADV_NOREUSE; - return sys_fadvise64(fd, offset, len, advise); -} - -struct fadvise64_64_args { - int fd; - long long offset; - long long len; - int advice; -}; - -asmlinkage long -sys32_fadvise64_64(struct fadvise64_64_args __user *args) -{ - struct fadvise64_64_args a; - - if ( copy_from_user(&a, args, sizeof(a)) ) - return -EFAULT; - if (a.advice == 4) - a.advice = POSIX_FADV_DONTNEED; - else if (a.advice == 5) - a.advice = POSIX_FADV_NOREUSE; - return sys_fadvise64_64(a.fd, a.offset, a.len, a.advice); -} diff --git a/ANDROID_3.4.5/arch/s390/kernel/compat_linux.h b/ANDROID_3.4.5/arch/s390/kernel/compat_linux.h deleted file mode 100644 index 9635d759..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/compat_linux.h +++ /dev/null @@ -1,227 +0,0 @@ -#ifndef _ASM_S390X_S390_H -#define _ASM_S390X_S390_H - -#include <linux/compat.h> -#include <linux/socket.h> -#include <linux/syscalls.h> - -/* Macro that masks the high order bit of an 32 bit pointer and converts it*/ -/* to a 64 bit pointer */ -#define A(__x) ((unsigned long)((__x) & 0x7FFFFFFFUL)) -#define AA(__x) \ - ((unsigned long)(__x)) - -/* Now 32bit compatibility types */ -struct ipc_kludge_32 { - __u32 msgp; /* pointer */ - __s32 msgtyp; -}; - -struct old_sigaction32 { - __u32 sa_handler; /* Really a pointer, but need to deal with 32 bits */ - compat_old_sigset_t sa_mask; /* A 32 bit mask */ - __u32 sa_flags; - __u32 sa_restorer; /* Another 32 bit pointer */ -}; - -typedef struct compat_siginfo { - int si_signo; - int si_errno; - int si_code; - - union { - int _pad[((128/sizeof(int)) - 3)]; - - /* kill() */ - struct { - pid_t _pid; /* sender's pid */ - uid_t _uid; /* sender's uid */ - } _kill; - - /* POSIX.1b timers */ - struct { - compat_timer_t _tid; /* timer id */ - int _overrun; /* overrun count */ - compat_sigval_t _sigval; /* same as below */ - int _sys_private; /* not to be passed to user */ - } _timer; - - /* POSIX.1b signals */ - struct { - pid_t _pid; /* sender's pid */ - uid_t _uid; /* sender's uid */ - compat_sigval_t _sigval; - } _rt; - - /* SIGCHLD */ - struct { - pid_t _pid; /* which child */ - uid_t _uid; /* sender's uid */ - int _status;/* exit code */ - compat_clock_t _utime; - compat_clock_t _stime; - } _sigchld; - - /* SIGILL, SIGFPE, SIGSEGV, SIGBUS */ - struct { - __u32 _addr; /* faulting insn/memory ref. - pointer */ - } _sigfault; - - /* SIGPOLL */ - struct { - int _band; /* POLL_IN, POLL_OUT, POLL_MSG */ - int _fd; - } _sigpoll; - } _sifields; -} compat_siginfo_t; - -/* - * How these fields are to be accessed. - */ -#define si_pid _sifields._kill._pid -#define si_uid _sifields._kill._uid -#define si_status _sifields._sigchld._status -#define si_utime _sifields._sigchld._utime -#define si_stime _sifields._sigchld._stime -#define si_value _sifields._rt._sigval -#define si_int _sifields._rt._sigval.sival_int -#define si_ptr _sifields._rt._sigval.sival_ptr -#define si_addr _sifields._sigfault._addr -#define si_band _sifields._sigpoll._band -#define si_fd _sifields._sigpoll._fd -#define si_tid _sifields._timer._tid -#define si_overrun _sifields._timer._overrun - -/* asm/sigcontext.h */ -typedef union -{ - __u64 d; - __u32 f; -} freg_t32; - -typedef struct -{ - unsigned int fpc; - freg_t32 fprs[__NUM_FPRS]; -} _s390_fp_regs32; - -typedef struct -{ - __u32 mask; - __u32 addr; -} _psw_t32 __attribute__ ((aligned(8))); - -typedef struct -{ - _psw_t32 psw; - __u32 gprs[__NUM_GPRS]; - __u32 acrs[__NUM_ACRS]; -} _s390_regs_common32; - -typedef struct -{ - _s390_regs_common32 regs; - _s390_fp_regs32 fpregs; -} _sigregs32; - -#define _SIGCONTEXT_NSIG32 64 -#define _SIGCONTEXT_NSIG_BPW32 32 -#define __SIGNAL_FRAMESIZE32 96 -#define _SIGMASK_COPY_SIZE32 (sizeof(u32)*2) - -struct sigcontext32 -{ - __u32 oldmask[_COMPAT_NSIG_WORDS]; - __u32 sregs; /* pointer */ -}; - -/* asm/signal.h */ -struct sigaction32 { - __u32 sa_handler; /* pointer */ - __u32 sa_flags; - __u32 sa_restorer; /* pointer */ - compat_sigset_t sa_mask; /* mask last for extensibility */ -}; - -typedef struct { - __u32 ss_sp; /* pointer */ - int ss_flags; - compat_size_t ss_size; -} stack_t32; - -/* asm/ucontext.h */ -struct ucontext32 { - __u32 uc_flags; - __u32 uc_link; /* pointer */ - stack_t32 uc_stack; - _sigregs32 uc_mcontext; - compat_sigset_t uc_sigmask; /* mask last for extensibility */ -}; - -struct stat64_emu31; -struct mmap_arg_struct_emu31; -struct fadvise64_64_args; -struct old_sigaction32; -struct old_sigaction32; - -long sys32_chown16(const char __user * filename, u16 user, u16 group); -long sys32_lchown16(const char __user * filename, u16 user, u16 group); -long sys32_fchown16(unsigned int fd, u16 user, u16 group); -long sys32_setregid16(u16 rgid, u16 egid); -long sys32_setgid16(u16 gid); -long sys32_setreuid16(u16 ruid, u16 euid); -long sys32_setuid16(u16 uid); -long sys32_setresuid16(u16 ruid, u16 euid, u16 suid); -long sys32_getresuid16(u16 __user *ruid, u16 __user *euid, u16 __user *suid); -long sys32_setresgid16(u16 rgid, u16 egid, u16 sgid); -long sys32_getresgid16(u16 __user *rgid, u16 __user *egid, u16 __user *sgid); -long sys32_setfsuid16(u16 uid); -long sys32_setfsgid16(u16 gid); -long sys32_getgroups16(int gidsetsize, u16 __user *grouplist); -long sys32_setgroups16(int gidsetsize, u16 __user *grouplist); -long sys32_getuid16(void); -long sys32_geteuid16(void); -long sys32_getgid16(void); -long sys32_getegid16(void); -long sys32_ipc(u32 call, int first, int second, int third, u32 ptr); -long sys32_truncate64(const char __user * path, unsigned long high, - unsigned long low); -long sys32_ftruncate64(unsigned int fd, unsigned long high, unsigned long low); -long sys32_sched_rr_get_interval(compat_pid_t pid, - struct compat_timespec __user *interval); -long sys32_rt_sigprocmask(int how, compat_sigset_t __user *set, - compat_sigset_t __user *oset, size_t sigsetsize); -long sys32_rt_sigpending(compat_sigset_t __user *set, size_t sigsetsize); -long sys32_rt_sigqueueinfo(int pid, int sig, compat_siginfo_t __user *uinfo); -long sys32_execve(const char __user *name, compat_uptr_t __user *argv, - compat_uptr_t __user *envp); -long sys32_init_module(void __user *umod, unsigned long len, - const char __user *uargs); -long sys32_delete_module(const char __user *name_user, unsigned int flags); -long sys32_pread64(unsigned int fd, char __user *ubuf, size_t count, - u32 poshi, u32 poslo); -long sys32_pwrite64(unsigned int fd, const char __user *ubuf, - size_t count, u32 poshi, u32 poslo); -compat_ssize_t sys32_readahead(int fd, u32 offhi, u32 offlo, s32 count); -long sys32_sendfile(int out_fd, int in_fd, compat_off_t __user *offset, - size_t count); -long sys32_sendfile64(int out_fd, int in_fd, compat_loff_t __user *offset, - s32 count); -long sys32_stat64(const char __user * filename, struct stat64_emu31 __user * statbuf); -long sys32_lstat64(const char __user * filename, - struct stat64_emu31 __user * statbuf); -long sys32_fstat64(unsigned long fd, struct stat64_emu31 __user * statbuf); -long sys32_fstatat64(unsigned int dfd, const char __user *filename, - struct stat64_emu31 __user* statbuf, int flag); -unsigned long old32_mmap(struct mmap_arg_struct_emu31 __user *arg); -long sys32_mmap2(struct mmap_arg_struct_emu31 __user *arg); -long sys32_read(unsigned int fd, char __user * buf, size_t count); -long sys32_write(unsigned int fd, const char __user * buf, size_t count); -long sys32_fadvise64(int fd, loff_t offset, size_t len, int advise); -long sys32_fadvise64_64(struct fadvise64_64_args __user *args); -long sys32_sigaction(int sig, const struct old_sigaction32 __user *act, - struct old_sigaction32 __user *oact); -long sys32_rt_sigaction(int sig, const struct sigaction32 __user *act, - struct sigaction32 __user *oact, size_t sigsetsize); -long sys32_sigaltstack(const stack_t32 __user *uss, stack_t32 __user *uoss); -#endif /* _ASM_S390X_S390_H */ diff --git a/ANDROID_3.4.5/arch/s390/kernel/compat_ptrace.h b/ANDROID_3.4.5/arch/s390/kernel/compat_ptrace.h deleted file mode 100644 index 12b82383..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/compat_ptrace.h +++ /dev/null @@ -1,63 +0,0 @@ -#ifndef _PTRACE32_H -#define _PTRACE32_H - -#include <asm/ptrace.h> /* needed for NUM_CR_WORDS */ -#include "compat_linux.h" /* needed for psw_compat_t */ - -struct compat_per_struct_kernel { - __u32 cr9; /* PER control bits */ - __u32 cr10; /* PER starting address */ - __u32 cr11; /* PER ending address */ - __u32 bits; /* Obsolete software bits */ - __u32 starting_addr; /* User specified start address */ - __u32 ending_addr; /* User specified end address */ - __u16 perc_atmid; /* PER trap ATMID */ - __u32 address; /* PER trap instruction address */ - __u8 access_id; /* PER trap access identification */ -}; - -struct compat_user_regs_struct -{ - psw_compat_t psw; - u32 gprs[NUM_GPRS]; - u32 acrs[NUM_ACRS]; - u32 orig_gpr2; - /* nb: there's a 4-byte hole here */ - s390_fp_regs fp_regs; - /* - * These per registers are in here so that gdb can modify them - * itself as there is no "official" ptrace interface for hardware - * watchpoints. This is the way intel does it. - */ - struct compat_per_struct_kernel per_info; - u32 ieee_instruction_pointer; /* obsolete, always 0 */ -}; - -struct compat_user { - /* We start with the registers, to mimic the way that "memory" - is returned from the ptrace(3,...) function. */ - struct compat_user_regs_struct regs; - /* The rest of this junk is to help gdb figure out what goes where */ - u32 u_tsize; /* Text segment size (pages). */ - u32 u_dsize; /* Data segment size (pages). */ - u32 u_ssize; /* Stack segment size (pages). */ - u32 start_code; /* Starting virtual address of text. */ - u32 start_stack; /* Starting virtual address of stack area. - This is actually the bottom of the stack, - the top of the stack is always found in the - esp register. */ - s32 signal; /* Signal that caused the core dump. */ - u32 u_ar0; /* Used by gdb to help find the values for */ - /* the registers. */ - u32 magic; /* To uniquely identify a core file */ - char u_comm[32]; /* User command that was responsible */ -}; - -typedef struct -{ - __u32 len; - __u32 kernel_addr; - __u32 process_addr; -} compat_ptrace_area; - -#endif /* _PTRACE32_H */ diff --git a/ANDROID_3.4.5/arch/s390/kernel/compat_signal.c b/ANDROID_3.4.5/arch/s390/kernel/compat_signal.c deleted file mode 100644 index 28040fd5..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/compat_signal.c +++ /dev/null @@ -1,597 +0,0 @@ -/* - * arch/s390/kernel/compat_signal.c - * - * Copyright (C) IBM Corp. 2000,2006 - * Author(s): Denis Joseph Barrow (djbarrow@de.ibm.com,barrow_dj@yahoo.com) - * Gerhard Tonn (ton@de.ibm.com) - * - * Copyright (C) 1991, 1992 Linus Torvalds - * - * 1997-11-28 Modified for POSIX.1b signals by Richard Henderson - */ - -#include <linux/compat.h> -#include <linux/sched.h> -#include <linux/mm.h> -#include <linux/smp.h> -#include <linux/kernel.h> -#include <linux/signal.h> -#include <linux/errno.h> -#include <linux/wait.h> -#include <linux/ptrace.h> -#include <linux/unistd.h> -#include <linux/stddef.h> -#include <linux/tty.h> -#include <linux/personality.h> -#include <linux/binfmts.h> -#include <asm/ucontext.h> -#include <asm/uaccess.h> -#include <asm/lowcore.h> -#include <asm/switch_to.h> -#include "compat_linux.h" -#include "compat_ptrace.h" -#include "entry.h" - -#define _BLOCKABLE (~(sigmask(SIGKILL) | sigmask(SIGSTOP))) - -typedef struct -{ - __u8 callee_used_stack[__SIGNAL_FRAMESIZE32]; - struct sigcontext32 sc; - _sigregs32 sregs; - int signo; - __u32 gprs_high[NUM_GPRS]; - __u8 retcode[S390_SYSCALL_SIZE]; -} sigframe32; - -typedef struct -{ - __u8 callee_used_stack[__SIGNAL_FRAMESIZE32]; - __u8 retcode[S390_SYSCALL_SIZE]; - compat_siginfo_t info; - struct ucontext32 uc; - __u32 gprs_high[NUM_GPRS]; -} rt_sigframe32; - -int copy_siginfo_to_user32(compat_siginfo_t __user *to, siginfo_t *from) -{ - int err; - - if (!access_ok (VERIFY_WRITE, to, sizeof(compat_siginfo_t))) - return -EFAULT; - - /* If you change siginfo_t structure, please be sure - this code is fixed accordingly. - It should never copy any pad contained in the structure - to avoid security leaks, but must copy the generic - 3 ints plus the relevant union member. - This routine must convert siginfo from 64bit to 32bit as well - at the same time. */ - err = __put_user(from->si_signo, &to->si_signo); - err |= __put_user(from->si_errno, &to->si_errno); - err |= __put_user((short)from->si_code, &to->si_code); - if (from->si_code < 0) - err |= __copy_to_user(&to->_sifields._pad, &from->_sifields._pad, SI_PAD_SIZE); - else { - switch (from->si_code >> 16) { - case __SI_RT >> 16: /* This is not generated by the kernel as of now. */ - case __SI_MESGQ >> 16: - err |= __put_user(from->si_int, &to->si_int); - /* fallthrough */ - case __SI_KILL >> 16: - err |= __put_user(from->si_pid, &to->si_pid); - err |= __put_user(from->si_uid, &to->si_uid); - break; - case __SI_CHLD >> 16: - err |= __put_user(from->si_pid, &to->si_pid); - err |= __put_user(from->si_uid, &to->si_uid); - err |= __put_user(from->si_utime, &to->si_utime); - err |= __put_user(from->si_stime, &to->si_stime); - err |= __put_user(from->si_status, &to->si_status); - break; - case __SI_FAULT >> 16: - err |= __put_user((unsigned long) from->si_addr, - &to->si_addr); - break; - case __SI_POLL >> 16: - err |= __put_user(from->si_band, &to->si_band); - err |= __put_user(from->si_fd, &to->si_fd); - break; - case __SI_TIMER >> 16: - err |= __put_user(from->si_tid, &to->si_tid); - err |= __put_user(from->si_overrun, &to->si_overrun); - err |= __put_user(from->si_int, &to->si_int); - break; - default: - break; - } - } - return err; -} - -int copy_siginfo_from_user32(siginfo_t *to, compat_siginfo_t __user *from) -{ - int err; - u32 tmp; - - if (!access_ok (VERIFY_READ, from, sizeof(compat_siginfo_t))) - return -EFAULT; - - err = __get_user(to->si_signo, &from->si_signo); - err |= __get_user(to->si_errno, &from->si_errno); - err |= __get_user(to->si_code, &from->si_code); - - if (to->si_code < 0) - err |= __copy_from_user(&to->_sifields._pad, &from->_sifields._pad, SI_PAD_SIZE); - else { - switch (to->si_code >> 16) { - case __SI_RT >> 16: /* This is not generated by the kernel as of now. */ - case __SI_MESGQ >> 16: - err |= __get_user(to->si_int, &from->si_int); - /* fallthrough */ - case __SI_KILL >> 16: - err |= __get_user(to->si_pid, &from->si_pid); - err |= __get_user(to->si_uid, &from->si_uid); - break; - case __SI_CHLD >> 16: - err |= __get_user(to->si_pid, &from->si_pid); - err |= __get_user(to->si_uid, &from->si_uid); - err |= __get_user(to->si_utime, &from->si_utime); - err |= __get_user(to->si_stime, &from->si_stime); - err |= __get_user(to->si_status, &from->si_status); - break; - case __SI_FAULT >> 16: - err |= __get_user(tmp, &from->si_addr); - to->si_addr = (void __force __user *) - (u64) (tmp & PSW32_ADDR_INSN); - break; - case __SI_POLL >> 16: - err |= __get_user(to->si_band, &from->si_band); - err |= __get_user(to->si_fd, &from->si_fd); - break; - case __SI_TIMER >> 16: - err |= __get_user(to->si_tid, &from->si_tid); - err |= __get_user(to->si_overrun, &from->si_overrun); - err |= __get_user(to->si_int, &from->si_int); - break; - default: - break; - } - } - return err; -} - -asmlinkage long -sys32_sigaction(int sig, const struct old_sigaction32 __user *act, - struct old_sigaction32 __user *oact) -{ - struct k_sigaction new_ka, old_ka; - unsigned long sa_handler, sa_restorer; - int ret; - - if (act) { - compat_old_sigset_t mask; - if (!access_ok(VERIFY_READ, act, sizeof(*act)) || - __get_user(sa_handler, &act->sa_handler) || - __get_user(sa_restorer, &act->sa_restorer) || - __get_user(new_ka.sa.sa_flags, &act->sa_flags) || - __get_user(mask, &act->sa_mask)) - return -EFAULT; - new_ka.sa.sa_handler = (__sighandler_t) sa_handler; - new_ka.sa.sa_restorer = (void (*)(void)) sa_restorer; - siginitset(&new_ka.sa.sa_mask, mask); - } - - ret = do_sigaction(sig, act ? &new_ka : NULL, oact ? &old_ka : NULL); - - if (!ret && oact) { - sa_handler = (unsigned long) old_ka.sa.sa_handler; - sa_restorer = (unsigned long) old_ka.sa.sa_restorer; - if (!access_ok(VERIFY_WRITE, oact, sizeof(*oact)) || - __put_user(sa_handler, &oact->sa_handler) || - __put_user(sa_restorer, &oact->sa_restorer) || - __put_user(old_ka.sa.sa_flags, &oact->sa_flags) || - __put_user(old_ka.sa.sa_mask.sig[0], &oact->sa_mask)) - return -EFAULT; - } - - return ret; -} - -asmlinkage long -sys32_rt_sigaction(int sig, const struct sigaction32 __user *act, - struct sigaction32 __user *oact, size_t sigsetsize) -{ - struct k_sigaction new_ka, old_ka; - unsigned long sa_handler; - int ret; - compat_sigset_t set32; - - /* XXX: Don't preclude handling different sized sigset_t's. */ - if (sigsetsize != sizeof(compat_sigset_t)) - return -EINVAL; - - if (act) { - ret = get_user(sa_handler, &act->sa_handler); - ret |= __copy_from_user(&set32, &act->sa_mask, - sizeof(compat_sigset_t)); - new_ka.sa.sa_mask.sig[0] = - set32.sig[0] | (((long)set32.sig[1]) << 32); - ret |= __get_user(new_ka.sa.sa_flags, &act->sa_flags); - - if (ret) - return -EFAULT; - new_ka.sa.sa_handler = (__sighandler_t) sa_handler; - } - - ret = do_sigaction(sig, act ? &new_ka : NULL, oact ? &old_ka : NULL); - - if (!ret && oact) { - set32.sig[1] = (old_ka.sa.sa_mask.sig[0] >> 32); - set32.sig[0] = old_ka.sa.sa_mask.sig[0]; - ret = put_user((unsigned long)old_ka.sa.sa_handler, &oact->sa_handler); - ret |= __copy_to_user(&oact->sa_mask, &set32, - sizeof(compat_sigset_t)); - ret |= __put_user(old_ka.sa.sa_flags, &oact->sa_flags); - } - - return ret; -} - -asmlinkage long -sys32_sigaltstack(const stack_t32 __user *uss, stack_t32 __user *uoss) -{ - struct pt_regs *regs = task_pt_regs(current); - stack_t kss, koss; - unsigned long ss_sp; - int ret, err = 0; - mm_segment_t old_fs = get_fs(); - - if (uss) { - if (!access_ok(VERIFY_READ, uss, sizeof(*uss))) - return -EFAULT; - err |= __get_user(ss_sp, &uss->ss_sp); - err |= __get_user(kss.ss_size, &uss->ss_size); - err |= __get_user(kss.ss_flags, &uss->ss_flags); - if (err) - return -EFAULT; - kss.ss_sp = (void __user *) ss_sp; - } - - set_fs (KERNEL_DS); - ret = do_sigaltstack((stack_t __force __user *) (uss ? &kss : NULL), - (stack_t __force __user *) (uoss ? &koss : NULL), - regs->gprs[15]); - set_fs (old_fs); - - if (!ret && uoss) { - if (!access_ok(VERIFY_WRITE, uoss, sizeof(*uoss))) - return -EFAULT; - ss_sp = (unsigned long) koss.ss_sp; - err |= __put_user(ss_sp, &uoss->ss_sp); - err |= __put_user(koss.ss_size, &uoss->ss_size); - err |= __put_user(koss.ss_flags, &uoss->ss_flags); - if (err) - return -EFAULT; - } - return ret; -} - -static int save_sigregs32(struct pt_regs *regs, _sigregs32 __user *sregs) -{ - _s390_regs_common32 regs32; - int err, i; - - regs32.psw.mask = psw32_user_bits | - ((__u32)(regs->psw.mask >> 32) & PSW32_MASK_USER); - regs32.psw.addr = (__u32) regs->psw.addr | - (__u32)(regs->psw.mask & PSW_MASK_BA); - for (i = 0; i < NUM_GPRS; i++) - regs32.gprs[i] = (__u32) regs->gprs[i]; - save_access_regs(current->thread.acrs); - memcpy(regs32.acrs, current->thread.acrs, sizeof(regs32.acrs)); - err = __copy_to_user(&sregs->regs, ®s32, sizeof(regs32)); - if (err) - return err; - save_fp_regs(¤t->thread.fp_regs); - /* s390_fp_regs and _s390_fp_regs32 are the same ! */ - return __copy_to_user(&sregs->fpregs, ¤t->thread.fp_regs, - sizeof(_s390_fp_regs32)); -} - -static int restore_sigregs32(struct pt_regs *regs,_sigregs32 __user *sregs) -{ - _s390_regs_common32 regs32; - int err, i; - - /* Alwys make any pending restarted system call return -EINTR */ - current_thread_info()->restart_block.fn = do_no_restart_syscall; - - err = __copy_from_user(®s32, &sregs->regs, sizeof(regs32)); - if (err) - return err; - regs->psw.mask = (regs->psw.mask & ~PSW_MASK_USER) | - (__u64)(regs32.psw.mask & PSW32_MASK_USER) << 32 | - (__u64)(regs32.psw.addr & PSW32_ADDR_AMODE); - regs->psw.addr = (__u64)(regs32.psw.addr & PSW32_ADDR_INSN); - for (i = 0; i < NUM_GPRS; i++) - regs->gprs[i] = (__u64) regs32.gprs[i]; - memcpy(current->thread.acrs, regs32.acrs, sizeof(current->thread.acrs)); - restore_access_regs(current->thread.acrs); - - err = __copy_from_user(¤t->thread.fp_regs, &sregs->fpregs, - sizeof(_s390_fp_regs32)); - current->thread.fp_regs.fpc &= FPC_VALID_MASK; - if (err) - return err; - - restore_fp_regs(¤t->thread.fp_regs); - clear_thread_flag(TIF_SYSCALL); /* No longer in a system call */ - return 0; -} - -static int save_sigregs_gprs_high(struct pt_regs *regs, __u32 __user *uregs) -{ - __u32 gprs_high[NUM_GPRS]; - int i; - - for (i = 0; i < NUM_GPRS; i++) - gprs_high[i] = regs->gprs[i] >> 32; - - return __copy_to_user(uregs, &gprs_high, sizeof(gprs_high)); -} - -static int restore_sigregs_gprs_high(struct pt_regs *regs, __u32 __user *uregs) -{ - __u32 gprs_high[NUM_GPRS]; - int err, i; - - err = __copy_from_user(&gprs_high, uregs, sizeof(gprs_high)); - if (err) - return err; - for (i = 0; i < NUM_GPRS; i++) - *(__u32 *)®s->gprs[i] = gprs_high[i]; - return 0; -} - -asmlinkage long sys32_sigreturn(void) -{ - struct pt_regs *regs = task_pt_regs(current); - sigframe32 __user *frame = (sigframe32 __user *)regs->gprs[15]; - sigset_t set; - - if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) - goto badframe; - if (__copy_from_user(&set.sig, &frame->sc.oldmask, _SIGMASK_COPY_SIZE32)) - goto badframe; - sigdelsetmask(&set, ~_BLOCKABLE); - set_current_blocked(&set); - if (restore_sigregs32(regs, &frame->sregs)) - goto badframe; - if (restore_sigregs_gprs_high(regs, frame->gprs_high)) - goto badframe; - return regs->gprs[2]; -badframe: - force_sig(SIGSEGV, current); - return 0; -} - -asmlinkage long sys32_rt_sigreturn(void) -{ - struct pt_regs *regs = task_pt_regs(current); - rt_sigframe32 __user *frame = (rt_sigframe32 __user *)regs->gprs[15]; - sigset_t set; - stack_t st; - __u32 ss_sp; - int err; - mm_segment_t old_fs = get_fs(); - - if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) - goto badframe; - if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) - goto badframe; - sigdelsetmask(&set, ~_BLOCKABLE); - set_current_blocked(&set); - if (restore_sigregs32(regs, &frame->uc.uc_mcontext)) - goto badframe; - if (restore_sigregs_gprs_high(regs, frame->gprs_high)) - goto badframe; - err = __get_user(ss_sp, &frame->uc.uc_stack.ss_sp); - st.ss_sp = compat_ptr(ss_sp); - err |= __get_user(st.ss_size, &frame->uc.uc_stack.ss_size); - err |= __get_user(st.ss_flags, &frame->uc.uc_stack.ss_flags); - if (err) - goto badframe; - set_fs (KERNEL_DS); - do_sigaltstack((stack_t __force __user *)&st, NULL, regs->gprs[15]); - set_fs (old_fs); - return regs->gprs[2]; -badframe: - force_sig(SIGSEGV, current); - return 0; -} - -/* - * Set up a signal frame. - */ - - -/* - * Determine which stack to use.. - */ -static inline void __user * -get_sigframe(struct k_sigaction *ka, struct pt_regs * regs, size_t frame_size) -{ - unsigned long sp; - - /* Default to using normal stack */ - sp = (unsigned long) A(regs->gprs[15]); - - /* Overflow on alternate signal stack gives SIGSEGV. */ - if (on_sig_stack(sp) && !on_sig_stack((sp - frame_size) & -8UL)) - return (void __user *) -1UL; - - /* This is the X/Open sanctioned signal stack switching. */ - if (ka->sa.sa_flags & SA_ONSTACK) { - if (! sas_ss_flags(sp)) - sp = current->sas_ss_sp + current->sas_ss_size; - } - - /* This is the legacy signal stack switching. */ - else if (!user_mode(regs) && - !(ka->sa.sa_flags & SA_RESTORER) && - ka->sa.sa_restorer) { - sp = (unsigned long) ka->sa.sa_restorer; - } - - return (void __user *)((sp - frame_size) & -8ul); -} - -static inline int map_signal(int sig) -{ - if (current_thread_info()->exec_domain - && current_thread_info()->exec_domain->signal_invmap - && sig < 32) - return current_thread_info()->exec_domain->signal_invmap[sig]; - else - return sig; -} - -static int setup_frame32(int sig, struct k_sigaction *ka, - sigset_t *set, struct pt_regs * regs) -{ - sigframe32 __user *frame = get_sigframe(ka, regs, sizeof(sigframe32)); - if (!access_ok(VERIFY_WRITE, frame, sizeof(sigframe32))) - goto give_sigsegv; - - if (frame == (void __user *) -1UL) - goto give_sigsegv; - - if (__copy_to_user(&frame->sc.oldmask, &set->sig, _SIGMASK_COPY_SIZE32)) - goto give_sigsegv; - - if (save_sigregs32(regs, &frame->sregs)) - goto give_sigsegv; - if (save_sigregs_gprs_high(regs, frame->gprs_high)) - goto give_sigsegv; - if (__put_user((unsigned long) &frame->sregs, &frame->sc.sregs)) - goto give_sigsegv; - - /* Set up to return from userspace. If provided, use a stub - already in userspace. */ - if (ka->sa.sa_flags & SA_RESTORER) { - regs->gprs[14] = (__u64) ka->sa.sa_restorer | PSW32_ADDR_AMODE; - } else { - regs->gprs[14] = (__u64) frame->retcode | PSW32_ADDR_AMODE; - if (__put_user(S390_SYSCALL_OPCODE | __NR_sigreturn, - (u16 __force __user *)(frame->retcode))) - goto give_sigsegv; - } - - /* Set up backchain. */ - if (__put_user(regs->gprs[15], (unsigned int __user *) frame)) - goto give_sigsegv; - - /* Set up registers for signal handler */ - regs->gprs[15] = (__force __u64) frame; - regs->psw.mask |= PSW_MASK_BA; /* force amode 31 */ - regs->psw.addr = (__force __u64) ka->sa.sa_handler; - - regs->gprs[2] = map_signal(sig); - regs->gprs[3] = (__force __u64) &frame->sc; - - /* We forgot to include these in the sigcontext. - To avoid breaking binary compatibility, they are passed as args. */ - if (sig == SIGSEGV || sig == SIGBUS || sig == SIGILL || - sig == SIGTRAP || sig == SIGFPE) { - /* set extra registers only for synchronous signals */ - regs->gprs[4] = regs->int_code & 127; - regs->gprs[5] = regs->int_parm_long; - } - - /* Place signal number on stack to allow backtrace from handler. */ - if (__put_user(regs->gprs[2], (int __force __user *) &frame->signo)) - goto give_sigsegv; - return 0; - -give_sigsegv: - force_sigsegv(sig, current); - return -EFAULT; -} - -static int setup_rt_frame32(int sig, struct k_sigaction *ka, siginfo_t *info, - sigset_t *set, struct pt_regs * regs) -{ - int err = 0; - rt_sigframe32 __user *frame = get_sigframe(ka, regs, sizeof(rt_sigframe32)); - if (!access_ok(VERIFY_WRITE, frame, sizeof(rt_sigframe32))) - goto give_sigsegv; - - if (frame == (void __user *) -1UL) - goto give_sigsegv; - - if (copy_siginfo_to_user32(&frame->info, info)) - goto give_sigsegv; - - /* Create the ucontext. */ - err |= __put_user(UC_EXTENDED, &frame->uc.uc_flags); - err |= __put_user(0, &frame->uc.uc_link); - err |= __put_user(current->sas_ss_sp, &frame->uc.uc_stack.ss_sp); - err |= __put_user(sas_ss_flags(regs->gprs[15]), - &frame->uc.uc_stack.ss_flags); - err |= __put_user(current->sas_ss_size, &frame->uc.uc_stack.ss_size); - err |= save_sigregs32(regs, &frame->uc.uc_mcontext); - err |= save_sigregs_gprs_high(regs, frame->gprs_high); - err |= __copy_to_user(&frame->uc.uc_sigmask, set, sizeof(*set)); - if (err) - goto give_sigsegv; - - /* Set up to return from userspace. If provided, use a stub - already in userspace. */ - if (ka->sa.sa_flags & SA_RESTORER) { - regs->gprs[14] = (__u64) ka->sa.sa_restorer | PSW32_ADDR_AMODE; - } else { - regs->gprs[14] = (__u64) frame->retcode | PSW32_ADDR_AMODE; - err |= __put_user(S390_SYSCALL_OPCODE | __NR_rt_sigreturn, - (u16 __force __user *)(frame->retcode)); - } - - /* Set up backchain. */ - if (__put_user(regs->gprs[15], (unsigned int __force __user *) frame)) - goto give_sigsegv; - - /* Set up registers for signal handler */ - regs->gprs[15] = (__force __u64) frame; - regs->psw.mask |= PSW_MASK_BA; /* force amode 31 */ - regs->psw.addr = (__u64) ka->sa.sa_handler; - - regs->gprs[2] = map_signal(sig); - regs->gprs[3] = (__force __u64) &frame->info; - regs->gprs[4] = (__force __u64) &frame->uc; - return 0; - -give_sigsegv: - force_sigsegv(sig, current); - return -EFAULT; -} - -/* - * OK, we're invoking a handler - */ - -int handle_signal32(unsigned long sig, struct k_sigaction *ka, - siginfo_t *info, sigset_t *oldset, struct pt_regs *regs) -{ - int ret; - - /* Set up the stack frame */ - if (ka->sa.sa_flags & SA_SIGINFO) - ret = setup_rt_frame32(sig, ka, info, oldset, regs); - else - ret = setup_frame32(sig, ka, oldset, regs); - if (ret) - return ret; - block_sigmask(ka, sig); - return 0; -} - diff --git a/ANDROID_3.4.5/arch/s390/kernel/compat_wrapper.S b/ANDROID_3.4.5/arch/s390/kernel/compat_wrapper.S deleted file mode 100644 index ff605a39..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/compat_wrapper.S +++ /dev/null @@ -1,1649 +0,0 @@ -/* -* arch/s390/kernel/compat_wrapper.S -* wrapper for 31 bit compatible system calls. -* -* Copyright (C) IBM Corp. 2000,2006 -* Author(s): Gerhard Tonn (ton@de.ibm.com), -* Thomas Spatzier (tspat@de.ibm.com) -*/ - -#include <linux/linkage.h> - -ENTRY(sys32_exit_wrapper) - lgfr %r2,%r2 # int - jg sys_exit # branch to sys_exit - -ENTRY(sys32_read_wrapper) - llgfr %r2,%r2 # unsigned int - llgtr %r3,%r3 # char * - llgfr %r4,%r4 # size_t - jg sys32_read # branch to sys_read - -ENTRY(sys32_write_wrapper) - llgfr %r2,%r2 # unsigned int - llgtr %r3,%r3 # const char * - llgfr %r4,%r4 # size_t - jg sys32_write # branch to system call - -ENTRY(sys32_open_wrapper) - llgtr %r2,%r2 # const char * - lgfr %r3,%r3 # int - lgfr %r4,%r4 # int - jg sys_open # branch to system call - -ENTRY(sys32_close_wrapper) - llgfr %r2,%r2 # unsigned int - jg sys_close # branch to system call - -ENTRY(sys32_creat_wrapper) - llgtr %r2,%r2 # const char * - lgfr %r3,%r3 # int - jg sys_creat # branch to system call - -ENTRY(sys32_link_wrapper) - llgtr %r2,%r2 # const char * - llgtr %r3,%r3 # const char * - jg sys_link # branch to system call - -ENTRY(sys32_unlink_wrapper) - llgtr %r2,%r2 # const char * - jg sys_unlink # branch to system call - -ENTRY(sys32_chdir_wrapper) - llgtr %r2,%r2 # const char * - jg sys_chdir # branch to system call - -ENTRY(sys32_time_wrapper) - llgtr %r2,%r2 # int * - jg compat_sys_time # branch to system call - -ENTRY(sys32_mknod_wrapper) - llgtr %r2,%r2 # const char * - lgfr %r3,%r3 # int - llgfr %r4,%r4 # dev - jg sys_mknod # branch to system call - -ENTRY(sys32_chmod_wrapper) - llgtr %r2,%r2 # const char * - llgfr %r3,%r3 # mode_t - jg sys_chmod # branch to system call - -ENTRY(sys32_lchown16_wrapper) - llgtr %r2,%r2 # const char * - llgfr %r3,%r3 # __kernel_old_uid_emu31_t - llgfr %r4,%r4 # __kernel_old_uid_emu31_t - jg sys32_lchown16 # branch to system call - -ENTRY(sys32_lseek_wrapper) - llgfr %r2,%r2 # unsigned int - lgfr %r3,%r3 # off_t - llgfr %r4,%r4 # unsigned int - jg sys_lseek # branch to system call - -#sys32_getpid_wrapper # void - -ENTRY(sys32_mount_wrapper) - llgtr %r2,%r2 # char * - llgtr %r3,%r3 # char * - llgtr %r4,%r4 # char * - llgfr %r5,%r5 # unsigned long - llgtr %r6,%r6 # void * - jg compat_sys_mount # branch to system call - -ENTRY(sys32_oldumount_wrapper) - llgtr %r2,%r2 # char * - jg sys_oldumount # branch to system call - -ENTRY(sys32_setuid16_wrapper) - llgfr %r2,%r2 # __kernel_old_uid_emu31_t - jg sys32_setuid16 # branch to system call - -#sys32_getuid16_wrapper # void - -ENTRY(sys32_ptrace_wrapper) - lgfr %r2,%r2 # long - lgfr %r3,%r3 # long - llgtr %r4,%r4 # long - llgfr %r5,%r5 # long - jg compat_sys_ptrace # branch to system call - -ENTRY(sys32_alarm_wrapper) - llgfr %r2,%r2 # unsigned int - jg sys_alarm # branch to system call - -ENTRY(compat_sys_utime_wrapper) - llgtr %r2,%r2 # char * - llgtr %r3,%r3 # struct compat_utimbuf * - jg compat_sys_utime # branch to system call - -ENTRY(sys32_access_wrapper) - llgtr %r2,%r2 # const char * - lgfr %r3,%r3 # int - jg sys_access # branch to system call - -ENTRY(sys32_nice_wrapper) - lgfr %r2,%r2 # int - jg sys_nice # branch to system call - -#sys32_sync_wrapper # void - -ENTRY(sys32_kill_wrapper) - lgfr %r2,%r2 # int - lgfr %r3,%r3 # int - jg sys_kill # branch to system call - -ENTRY(sys32_rename_wrapper) - llgtr %r2,%r2 # const char * - llgtr %r3,%r3 # const char * - jg sys_rename # branch to system call - -ENTRY(sys32_mkdir_wrapper) - llgtr %r2,%r2 # const char * - lgfr %r3,%r3 # int - jg sys_mkdir # branch to system call - -ENTRY(sys32_rmdir_wrapper) - llgtr %r2,%r2 # const char * - jg sys_rmdir # branch to system call - -ENTRY(sys32_dup_wrapper) - llgfr %r2,%r2 # unsigned int - jg sys_dup # branch to system call - -ENTRY(sys32_pipe_wrapper) - llgtr %r2,%r2 # u32 * - jg sys_pipe # branch to system call - -ENTRY(compat_sys_times_wrapper) - llgtr %r2,%r2 # struct compat_tms * - jg compat_sys_times # branch to system call - -ENTRY(sys32_brk_wrapper) - llgtr %r2,%r2 # unsigned long - jg sys_brk # branch to system call - -ENTRY(sys32_setgid16_wrapper) - llgfr %r2,%r2 # __kernel_old_gid_emu31_t - jg sys32_setgid16 # branch to system call - -#sys32_getgid16_wrapper # void - -ENTRY(sys32_signal_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # __sighandler_t - jg sys_signal - -#sys32_geteuid16_wrapper # void - -#sys32_getegid16_wrapper # void - -ENTRY(sys32_acct_wrapper) - llgtr %r2,%r2 # char * - jg sys_acct # branch to system call - -ENTRY(sys32_umount_wrapper) - llgtr %r2,%r2 # char * - lgfr %r3,%r3 # int - jg sys_umount # branch to system call - -ENTRY(compat_sys_ioctl_wrapper) - llgfr %r2,%r2 # unsigned int - llgfr %r3,%r3 # unsigned int - llgfr %r4,%r4 # unsigned int - jg compat_sys_ioctl # branch to system call - -ENTRY(compat_sys_fcntl_wrapper) - llgfr %r2,%r2 # unsigned int - llgfr %r3,%r3 # unsigned int - llgfr %r4,%r4 # unsigned long - jg compat_sys_fcntl # branch to system call - -ENTRY(sys32_setpgid_wrapper) - lgfr %r2,%r2 # pid_t - lgfr %r3,%r3 # pid_t - jg sys_setpgid # branch to system call - -ENTRY(sys32_umask_wrapper) - lgfr %r2,%r2 # int - jg sys_umask # branch to system call - -ENTRY(sys32_chroot_wrapper) - llgtr %r2,%r2 # char * - jg sys_chroot # branch to system call - -ENTRY(sys32_ustat_wrapper) - llgfr %r2,%r2 # dev_t - llgtr %r3,%r3 # struct ustat * - jg compat_sys_ustat - -ENTRY(sys32_dup2_wrapper) - llgfr %r2,%r2 # unsigned int - llgfr %r3,%r3 # unsigned int - jg sys_dup2 # branch to system call - -#sys32_getppid_wrapper # void - -#sys32_getpgrp_wrapper # void - -#sys32_setsid_wrapper # void - -ENTRY(sys32_sigaction_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # const struct old_sigaction * - llgtr %r4,%r4 # struct old_sigaction32 * - jg sys32_sigaction # branch to system call - -ENTRY(sys32_setreuid16_wrapper) - llgfr %r2,%r2 # __kernel_old_uid_emu31_t - llgfr %r3,%r3 # __kernel_old_uid_emu31_t - jg sys32_setreuid16 # branch to system call - -ENTRY(sys32_setregid16_wrapper) - llgfr %r2,%r2 # __kernel_old_gid_emu31_t - llgfr %r3,%r3 # __kernel_old_gid_emu31_t - jg sys32_setregid16 # branch to system call - -ENTRY(sys_sigsuspend_wrapper) - lgfr %r2,%r2 # int - lgfr %r3,%r3 # int - llgfr %r4,%r4 # old_sigset_t - jg sys_sigsuspend - -ENTRY(compat_sys_sigpending_wrapper) - llgtr %r2,%r2 # compat_old_sigset_t * - jg compat_sys_sigpending # branch to system call - -ENTRY(sys32_sethostname_wrapper) - llgtr %r2,%r2 # char * - lgfr %r3,%r3 # int - jg sys_sethostname # branch to system call - -ENTRY(compat_sys_setrlimit_wrapper) - llgfr %r2,%r2 # unsigned int - llgtr %r3,%r3 # struct rlimit_emu31 * - jg compat_sys_setrlimit # branch to system call - -ENTRY(compat_sys_old_getrlimit_wrapper) - llgfr %r2,%r2 # unsigned int - llgtr %r3,%r3 # struct rlimit_emu31 * - jg compat_sys_old_getrlimit # branch to system call - -ENTRY(compat_sys_getrlimit_wrapper) - llgfr %r2,%r2 # unsigned int - llgtr %r3,%r3 # struct rlimit_emu31 * - jg compat_sys_getrlimit # branch to system call - -ENTRY(sys32_mmap2_wrapper) - llgtr %r2,%r2 # struct mmap_arg_struct_emu31 * - jg sys32_mmap2 # branch to system call - -ENTRY(compat_sys_getrusage_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # struct rusage_emu31 * - jg compat_sys_getrusage # branch to system call - -ENTRY(compat_sys_gettimeofday_wrapper) - llgtr %r2,%r2 # struct timeval_emu31 * - llgtr %r3,%r3 # struct timezone * - jg compat_sys_gettimeofday # branch to system call - -ENTRY(compat_sys_settimeofday_wrapper) - llgtr %r2,%r2 # struct timeval_emu31 * - llgtr %r3,%r3 # struct timezone * - jg compat_sys_settimeofday # branch to system call - -ENTRY(sys32_getgroups16_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # __kernel_old_gid_emu31_t * - jg sys32_getgroups16 # branch to system call - -ENTRY(sys32_setgroups16_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # __kernel_old_gid_emu31_t * - jg sys32_setgroups16 # branch to system call - -ENTRY(sys32_symlink_wrapper) - llgtr %r2,%r2 # const char * - llgtr %r3,%r3 # const char * - jg sys_symlink # branch to system call - -ENTRY(sys32_readlink_wrapper) - llgtr %r2,%r2 # const char * - llgtr %r3,%r3 # char * - lgfr %r4,%r4 # int - jg sys_readlink # branch to system call - -ENTRY(sys32_uselib_wrapper) - llgtr %r2,%r2 # const char * - jg sys_uselib # branch to system call - -ENTRY(sys32_swapon_wrapper) - llgtr %r2,%r2 # const char * - lgfr %r3,%r3 # int - jg sys_swapon # branch to system call - -ENTRY(sys32_reboot_wrapper) - lgfr %r2,%r2 # int - lgfr %r3,%r3 # int - llgfr %r4,%r4 # unsigned int - llgtr %r5,%r5 # void * - jg sys_reboot # branch to system call - -ENTRY(old32_readdir_wrapper) - llgfr %r2,%r2 # unsigned int - llgtr %r3,%r3 # void * - llgfr %r4,%r4 # unsigned int - jg compat_sys_old_readdir # branch to system call - -ENTRY(old32_mmap_wrapper) - llgtr %r2,%r2 # struct mmap_arg_struct_emu31 * - jg old32_mmap # branch to system call - -ENTRY(sys32_munmap_wrapper) - llgfr %r2,%r2 # unsigned long - llgfr %r3,%r3 # size_t - jg sys_munmap # branch to system call - -ENTRY(sys32_truncate_wrapper) - llgtr %r2,%r2 # const char * - lgfr %r3,%r3 # long - jg sys_truncate # branch to system call - -ENTRY(sys32_ftruncate_wrapper) - llgfr %r2,%r2 # unsigned int - llgfr %r3,%r3 # unsigned long - jg sys_ftruncate # branch to system call - -ENTRY(sys32_fchmod_wrapper) - llgfr %r2,%r2 # unsigned int - llgfr %r3,%r3 # mode_t - jg sys_fchmod # branch to system call - -ENTRY(sys32_fchown16_wrapper) - llgfr %r2,%r2 # unsigned int - llgfr %r3,%r3 # compat_uid_t - llgfr %r4,%r4 # compat_uid_t - jg sys32_fchown16 # branch to system call - -ENTRY(sys32_getpriority_wrapper) - lgfr %r2,%r2 # int - lgfr %r3,%r3 # int - jg sys_getpriority # branch to system call - -ENTRY(sys32_setpriority_wrapper) - lgfr %r2,%r2 # int - lgfr %r3,%r3 # int - lgfr %r4,%r4 # int - jg sys_setpriority # branch to system call - -ENTRY(compat_sys_statfs_wrapper) - llgtr %r2,%r2 # char * - llgtr %r3,%r3 # struct compat_statfs * - jg compat_sys_statfs # branch to system call - -ENTRY(compat_sys_fstatfs_wrapper) - llgfr %r2,%r2 # unsigned int - llgtr %r3,%r3 # struct compat_statfs * - jg compat_sys_fstatfs # branch to system call - -ENTRY(compat_sys_socketcall_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # u32 * - jg compat_sys_socketcall # branch to system call - -ENTRY(sys32_syslog_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # char * - lgfr %r4,%r4 # int - jg sys_syslog # branch to system call - -ENTRY(compat_sys_setitimer_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # struct itimerval_emu31 * - llgtr %r4,%r4 # struct itimerval_emu31 * - jg compat_sys_setitimer # branch to system call - -ENTRY(compat_sys_getitimer_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # struct itimerval_emu31 * - jg compat_sys_getitimer # branch to system call - -ENTRY(compat_sys_newstat_wrapper) - llgtr %r2,%r2 # char * - llgtr %r3,%r3 # struct stat_emu31 * - jg compat_sys_newstat # branch to system call - -ENTRY(compat_sys_newlstat_wrapper) - llgtr %r2,%r2 # char * - llgtr %r3,%r3 # struct stat_emu31 * - jg compat_sys_newlstat # branch to system call - -ENTRY(compat_sys_newfstat_wrapper) - llgfr %r2,%r2 # unsigned int - llgtr %r3,%r3 # struct stat_emu31 * - jg compat_sys_newfstat # branch to system call - -#sys32_vhangup_wrapper # void - -ENTRY(compat_sys_wait4_wrapper) - lgfr %r2,%r2 # pid_t - llgtr %r3,%r3 # unsigned int * - lgfr %r4,%r4 # int - llgtr %r5,%r5 # struct rusage * - jg compat_sys_wait4 # branch to system call - -ENTRY(sys32_swapoff_wrapper) - llgtr %r2,%r2 # const char * - jg sys_swapoff # branch to system call - -ENTRY(compat_sys_sysinfo_wrapper) - llgtr %r2,%r2 # struct sysinfo_emu31 * - jg compat_sys_sysinfo # branch to system call - -ENTRY(sys32_ipc_wrapper) - llgfr %r2,%r2 # uint - lgfr %r3,%r3 # int - lgfr %r4,%r4 # int - lgfr %r5,%r5 # int - llgfr %r6,%r6 # u32 - jg sys32_ipc # branch to system call - -ENTRY(sys32_fsync_wrapper) - llgfr %r2,%r2 # unsigned int - jg sys_fsync # branch to system call - -#sys32_sigreturn_wrapper # done in sigreturn_glue - -#sys32_clone_wrapper # done in clone_glue - -ENTRY(sys32_setdomainname_wrapper) - llgtr %r2,%r2 # char * - lgfr %r3,%r3 # int - jg sys_setdomainname # branch to system call - -ENTRY(sys32_newuname_wrapper) - llgtr %r2,%r2 # struct new_utsname * - jg sys_newuname # branch to system call - -ENTRY(compat_sys_adjtimex_wrapper) - llgtr %r2,%r2 # struct compat_timex * - jg compat_sys_adjtimex # branch to system call - -ENTRY(sys32_mprotect_wrapper) - llgtr %r2,%r2 # unsigned long (actually pointer - llgfr %r3,%r3 # size_t - llgfr %r4,%r4 # unsigned long - jg sys_mprotect # branch to system call - -ENTRY(compat_sys_sigprocmask_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # compat_old_sigset_t * - llgtr %r4,%r4 # compat_old_sigset_t * - jg compat_sys_sigprocmask # branch to system call - -ENTRY(sys_init_module_wrapper) - llgtr %r2,%r2 # void * - llgfr %r3,%r3 # unsigned long - llgtr %r4,%r4 # char * - jg sys_init_module # branch to system call - -ENTRY(sys_delete_module_wrapper) - llgtr %r2,%r2 # const char * - llgfr %r3,%r3 # unsigned int - jg sys_delete_module # branch to system call - -ENTRY(sys32_quotactl_wrapper) - llgfr %r2,%r2 # unsigned int - llgtr %r3,%r3 # const char * - llgfr %r4,%r4 # qid_t - llgtr %r5,%r5 # caddr_t - jg sys_quotactl # branch to system call - -ENTRY(sys32_getpgid_wrapper) - lgfr %r2,%r2 # pid_t - jg sys_getpgid # branch to system call - -ENTRY(sys32_fchdir_wrapper) - llgfr %r2,%r2 # unsigned int - jg sys_fchdir # branch to system call - -ENTRY(sys32_bdflush_wrapper) - lgfr %r2,%r2 # int - lgfr %r3,%r3 # long - jg sys_bdflush # branch to system call - -ENTRY(sys32_sysfs_wrapper) - lgfr %r2,%r2 # int - llgfr %r3,%r3 # unsigned long - llgfr %r4,%r4 # unsigned long - jg sys_sysfs # branch to system call - -ENTRY(sys32_personality_wrapper) - llgfr %r2,%r2 # unsigned int - jg sys_s390_personality # branch to system call - -ENTRY(sys32_setfsuid16_wrapper) - llgfr %r2,%r2 # __kernel_old_uid_emu31_t - jg sys32_setfsuid16 # branch to system call - -ENTRY(sys32_setfsgid16_wrapper) - llgfr %r2,%r2 # __kernel_old_gid_emu31_t - jg sys32_setfsgid16 # branch to system call - -ENTRY(sys32_llseek_wrapper) - llgfr %r2,%r2 # unsigned int - llgfr %r3,%r3 # unsigned long - llgfr %r4,%r4 # unsigned long - llgtr %r5,%r5 # loff_t * - llgfr %r6,%r6 # unsigned int - jg sys_llseek # branch to system call - -ENTRY(sys32_getdents_wrapper) - llgfr %r2,%r2 # unsigned int - llgtr %r3,%r3 # void * - llgfr %r4,%r4 # unsigned int - jg compat_sys_getdents # branch to system call - -ENTRY(compat_sys_select_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # compat_fd_set * - llgtr %r4,%r4 # compat_fd_set * - llgtr %r5,%r5 # compat_fd_set * - llgtr %r6,%r6 # struct compat_timeval * - jg compat_sys_select # branch to system call - -ENTRY(sys32_flock_wrapper) - llgfr %r2,%r2 # unsigned int - llgfr %r3,%r3 # unsigned int - jg sys_flock # branch to system call - -ENTRY(sys32_msync_wrapper) - llgfr %r2,%r2 # unsigned long - llgfr %r3,%r3 # size_t - lgfr %r4,%r4 # int - jg sys_msync # branch to system call - -ENTRY(compat_sys_readv_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # const struct compat_iovec * - llgfr %r4,%r4 # unsigned long - jg compat_sys_readv # branch to system call - -ENTRY(compat_sys_writev_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # const struct compat_iovec * - llgfr %r4,%r4 # unsigned long - jg compat_sys_writev # branch to system call - -ENTRY(sys32_getsid_wrapper) - lgfr %r2,%r2 # pid_t - jg sys_getsid # branch to system call - -ENTRY(sys32_fdatasync_wrapper) - llgfr %r2,%r2 # unsigned int - jg sys_fdatasync # branch to system call - -ENTRY(sys32_mlock_wrapper) - llgfr %r2,%r2 # unsigned long - llgfr %r3,%r3 # size_t - jg sys_mlock # branch to system call - -ENTRY(sys32_munlock_wrapper) - llgfr %r2,%r2 # unsigned long - llgfr %r3,%r3 # size_t - jg sys_munlock # branch to system call - -ENTRY(sys32_mlockall_wrapper) - lgfr %r2,%r2 # int - jg sys_mlockall # branch to system call - -#sys32_munlockall_wrapper # void - -ENTRY(sys32_sched_setparam_wrapper) - lgfr %r2,%r2 # pid_t - llgtr %r3,%r3 # struct sched_param * - jg sys_sched_setparam # branch to system call - -ENTRY(sys32_sched_getparam_wrapper) - lgfr %r2,%r2 # pid_t - llgtr %r3,%r3 # struct sched_param * - jg sys_sched_getparam # branch to system call - -ENTRY(sys32_sched_setscheduler_wrapper) - lgfr %r2,%r2 # pid_t - lgfr %r3,%r3 # int - llgtr %r4,%r4 # struct sched_param * - jg sys_sched_setscheduler # branch to system call - -ENTRY(sys32_sched_getscheduler_wrapper) - lgfr %r2,%r2 # pid_t - jg sys_sched_getscheduler # branch to system call - -#sys32_sched_yield_wrapper # void - -ENTRY(sys32_sched_get_priority_max_wrapper) - lgfr %r2,%r2 # int - jg sys_sched_get_priority_max # branch to system call - -ENTRY(sys32_sched_get_priority_min_wrapper) - lgfr %r2,%r2 # int - jg sys_sched_get_priority_min # branch to system call - -ENTRY(sys32_sched_rr_get_interval_wrapper) - lgfr %r2,%r2 # pid_t - llgtr %r3,%r3 # struct compat_timespec * - jg sys32_sched_rr_get_interval # branch to system call - -ENTRY(compat_sys_nanosleep_wrapper) - llgtr %r2,%r2 # struct compat_timespec * - llgtr %r3,%r3 # struct compat_timespec * - jg compat_sys_nanosleep # branch to system call - -ENTRY(sys32_mremap_wrapper) - llgfr %r2,%r2 # unsigned long - llgfr %r3,%r3 # unsigned long - llgfr %r4,%r4 # unsigned long - llgfr %r5,%r5 # unsigned long - llgfr %r6,%r6 # unsigned long - jg sys_mremap # branch to system call - -ENTRY(sys32_setresuid16_wrapper) - llgfr %r2,%r2 # __kernel_old_uid_emu31_t - llgfr %r3,%r3 # __kernel_old_uid_emu31_t - llgfr %r4,%r4 # __kernel_old_uid_emu31_t - jg sys32_setresuid16 # branch to system call - -ENTRY(sys32_getresuid16_wrapper) - llgtr %r2,%r2 # __kernel_old_uid_emu31_t * - llgtr %r3,%r3 # __kernel_old_uid_emu31_t * - llgtr %r4,%r4 # __kernel_old_uid_emu31_t * - jg sys32_getresuid16 # branch to system call - -ENTRY(sys32_poll_wrapper) - llgtr %r2,%r2 # struct pollfd * - llgfr %r3,%r3 # unsigned int - lgfr %r4,%r4 # int - jg sys_poll # branch to system call - -ENTRY(sys32_setresgid16_wrapper) - llgfr %r2,%r2 # __kernel_old_gid_emu31_t - llgfr %r3,%r3 # __kernel_old_gid_emu31_t - llgfr %r4,%r4 # __kernel_old_gid_emu31_t - jg sys32_setresgid16 # branch to system call - -ENTRY(sys32_getresgid16_wrapper) - llgtr %r2,%r2 # __kernel_old_gid_emu31_t * - llgtr %r3,%r3 # __kernel_old_gid_emu31_t * - llgtr %r4,%r4 # __kernel_old_gid_emu31_t * - jg sys32_getresgid16 # branch to system call - -ENTRY(sys32_prctl_wrapper) - lgfr %r2,%r2 # int - llgfr %r3,%r3 # unsigned long - llgfr %r4,%r4 # unsigned long - llgfr %r5,%r5 # unsigned long - llgfr %r6,%r6 # unsigned long - jg sys_prctl # branch to system call - -#sys32_rt_sigreturn_wrapper # done in rt_sigreturn_glue - -ENTRY(sys32_rt_sigaction_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # const struct sigaction_emu31 * - llgtr %r4,%r4 # const struct sigaction_emu31 * - llgfr %r5,%r5 # size_t - jg sys32_rt_sigaction # branch to system call - -ENTRY(sys32_rt_sigprocmask_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # old_sigset_emu31 * - llgtr %r4,%r4 # old_sigset_emu31 * - llgfr %r5,%r5 # size_t - jg sys32_rt_sigprocmask # branch to system call - -ENTRY(sys32_rt_sigpending_wrapper) - llgtr %r2,%r2 # sigset_emu31 * - llgfr %r3,%r3 # size_t - jg sys32_rt_sigpending # branch to system call - -ENTRY(compat_sys_rt_sigtimedwait_wrapper) - llgtr %r2,%r2 # const sigset_emu31_t * - llgtr %r3,%r3 # siginfo_emu31_t * - llgtr %r4,%r4 # const struct compat_timespec * - llgfr %r5,%r5 # size_t - jg compat_sys_rt_sigtimedwait # branch to system call - -ENTRY(sys32_rt_sigqueueinfo_wrapper) - lgfr %r2,%r2 # int - lgfr %r3,%r3 # int - llgtr %r4,%r4 # siginfo_emu31_t * - jg sys32_rt_sigqueueinfo # branch to system call - -ENTRY(compat_sys_rt_sigsuspend_wrapper) - llgtr %r2,%r2 # compat_sigset_t * - llgfr %r3,%r3 # compat_size_t - jg compat_sys_rt_sigsuspend - -ENTRY(sys32_pread64_wrapper) - llgfr %r2,%r2 # unsigned int - llgtr %r3,%r3 # char * - llgfr %r4,%r4 # size_t - llgfr %r5,%r5 # u32 - llgfr %r6,%r6 # u32 - jg sys32_pread64 # branch to system call - -ENTRY(sys32_pwrite64_wrapper) - llgfr %r2,%r2 # unsigned int - llgtr %r3,%r3 # const char * - llgfr %r4,%r4 # size_t - llgfr %r5,%r5 # u32 - llgfr %r6,%r6 # u32 - jg sys32_pwrite64 # branch to system call - -ENTRY(sys32_chown16_wrapper) - llgtr %r2,%r2 # const char * - llgfr %r3,%r3 # __kernel_old_uid_emu31_t - llgfr %r4,%r4 # __kernel_old_gid_emu31_t - jg sys32_chown16 # branch to system call - -ENTRY(sys32_getcwd_wrapper) - llgtr %r2,%r2 # char * - llgfr %r3,%r3 # unsigned long - jg sys_getcwd # branch to system call - -ENTRY(sys32_capget_wrapper) - llgtr %r2,%r2 # cap_user_header_t - llgtr %r3,%r3 # cap_user_data_t - jg sys_capget # branch to system call - -ENTRY(sys32_capset_wrapper) - llgtr %r2,%r2 # cap_user_header_t - llgtr %r3,%r3 # const cap_user_data_t - jg sys_capset # branch to system call - -ENTRY(sys32_sigaltstack_wrapper) - llgtr %r2,%r2 # const stack_emu31_t * - llgtr %r3,%r3 # stack_emu31_t * - jg sys32_sigaltstack - -ENTRY(sys32_sendfile_wrapper) - lgfr %r2,%r2 # int - lgfr %r3,%r3 # int - llgtr %r4,%r4 # __kernel_off_emu31_t * - llgfr %r5,%r5 # size_t - jg sys32_sendfile # branch to system call - -#sys32_vfork_wrapper # done in vfork_glue - -ENTRY(sys32_truncate64_wrapper) - llgtr %r2,%r2 # const char * - llgfr %r3,%r3 # unsigned long - llgfr %r4,%r4 # unsigned long - jg sys32_truncate64 # branch to system call - -ENTRY(sys32_ftruncate64_wrapper) - llgfr %r2,%r2 # unsigned int - llgfr %r3,%r3 # unsigned long - llgfr %r4,%r4 # unsigned long - jg sys32_ftruncate64 # branch to system call - -ENTRY(sys32_lchown_wrapper) - llgtr %r2,%r2 # const char * - llgfr %r3,%r3 # uid_t - llgfr %r4,%r4 # gid_t - jg sys_lchown # branch to system call - -#sys32_getuid_wrapper # void -#sys32_getgid_wrapper # void -#sys32_geteuid_wrapper # void -#sys32_getegid_wrapper # void - -ENTRY(sys32_setreuid_wrapper) - llgfr %r2,%r2 # uid_t - llgfr %r3,%r3 # uid_t - jg sys_setreuid # branch to system call - -ENTRY(sys32_setregid_wrapper) - llgfr %r2,%r2 # gid_t - llgfr %r3,%r3 # gid_t - jg sys_setregid # branch to system call - -ENTRY(sys32_getgroups_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # gid_t * - jg sys_getgroups # branch to system call - -ENTRY(sys32_setgroups_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # gid_t * - jg sys_setgroups # branch to system call - -ENTRY(sys32_fchown_wrapper) - llgfr %r2,%r2 # unsigned int - llgfr %r3,%r3 # uid_t - llgfr %r4,%r4 # gid_t - jg sys_fchown # branch to system call - -ENTRY(sys32_setresuid_wrapper) - llgfr %r2,%r2 # uid_t - llgfr %r3,%r3 # uid_t - llgfr %r4,%r4 # uid_t - jg sys_setresuid # branch to system call - -ENTRY(sys32_getresuid_wrapper) - llgtr %r2,%r2 # uid_t * - llgtr %r3,%r3 # uid_t * - llgtr %r4,%r4 # uid_t * - jg sys_getresuid # branch to system call - -ENTRY(sys32_setresgid_wrapper) - llgfr %r2,%r2 # gid_t - llgfr %r3,%r3 # gid_t - llgfr %r4,%r4 # gid_t - jg sys_setresgid # branch to system call - -ENTRY(sys32_getresgid_wrapper) - llgtr %r2,%r2 # gid_t * - llgtr %r3,%r3 # gid_t * - llgtr %r4,%r4 # gid_t * - jg sys_getresgid # branch to system call - -ENTRY(sys32_chown_wrapper) - llgtr %r2,%r2 # const char * - llgfr %r3,%r3 # uid_t - llgfr %r4,%r4 # gid_t - jg sys_chown # branch to system call - -ENTRY(sys32_setuid_wrapper) - llgfr %r2,%r2 # uid_t - jg sys_setuid # branch to system call - -ENTRY(sys32_setgid_wrapper) - llgfr %r2,%r2 # gid_t - jg sys_setgid # branch to system call - -ENTRY(sys32_setfsuid_wrapper) - llgfr %r2,%r2 # uid_t - jg sys_setfsuid # branch to system call - -ENTRY(sys32_setfsgid_wrapper) - llgfr %r2,%r2 # gid_t - jg sys_setfsgid # branch to system call - -ENTRY(sys32_pivot_root_wrapper) - llgtr %r2,%r2 # const char * - llgtr %r3,%r3 # const char * - jg sys_pivot_root # branch to system call - -ENTRY(sys32_mincore_wrapper) - llgfr %r2,%r2 # unsigned long - llgfr %r3,%r3 # size_t - llgtr %r4,%r4 # unsigned char * - jg sys_mincore # branch to system call - -ENTRY(sys32_madvise_wrapper) - llgfr %r2,%r2 # unsigned long - llgfr %r3,%r3 # size_t - lgfr %r4,%r4 # int - jg sys_madvise # branch to system call - -ENTRY(sys32_getdents64_wrapper) - llgfr %r2,%r2 # unsigned int - llgtr %r3,%r3 # void * - llgfr %r4,%r4 # unsigned int - jg sys_getdents64 # branch to system call - -ENTRY(compat_sys_fcntl64_wrapper) - llgfr %r2,%r2 # unsigned int - llgfr %r3,%r3 # unsigned int - llgfr %r4,%r4 # unsigned long - jg compat_sys_fcntl64 # branch to system call - -ENTRY(sys32_stat64_wrapper) - llgtr %r2,%r2 # char * - llgtr %r3,%r3 # struct stat64 * - jg sys32_stat64 # branch to system call - -ENTRY(sys32_lstat64_wrapper) - llgtr %r2,%r2 # char * - llgtr %r3,%r3 # struct stat64 * - jg sys32_lstat64 # branch to system call - -ENTRY(sys32_stime_wrapper) - llgtr %r2,%r2 # long * - jg compat_sys_stime # branch to system call - -ENTRY(sys32_sysctl_wrapper) - llgtr %r2,%r2 # struct compat_sysctl_args * - jg compat_sys_sysctl - -ENTRY(sys32_fstat64_wrapper) - llgfr %r2,%r2 # unsigned long - llgtr %r3,%r3 # struct stat64 * - jg sys32_fstat64 # branch to system call - -ENTRY(compat_sys_futex_wrapper) - llgtr %r2,%r2 # u32 * - lgfr %r3,%r3 # int - lgfr %r4,%r4 # int - llgtr %r5,%r5 # struct compat_timespec * - llgtr %r6,%r6 # u32 * - lgf %r0,164(%r15) # int - stg %r0,160(%r15) - jg compat_sys_futex # branch to system call - -ENTRY(sys32_setxattr_wrapper) - llgtr %r2,%r2 # char * - llgtr %r3,%r3 # char * - llgtr %r4,%r4 # void * - llgfr %r5,%r5 # size_t - lgfr %r6,%r6 # int - jg sys_setxattr - -ENTRY(sys32_lsetxattr_wrapper) - llgtr %r2,%r2 # char * - llgtr %r3,%r3 # char * - llgtr %r4,%r4 # void * - llgfr %r5,%r5 # size_t - lgfr %r6,%r6 # int - jg sys_lsetxattr - -ENTRY(sys32_fsetxattr_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # char * - llgtr %r4,%r4 # void * - llgfr %r5,%r5 # size_t - lgfr %r6,%r6 # int - jg sys_fsetxattr - -ENTRY(sys32_getxattr_wrapper) - llgtr %r2,%r2 # char * - llgtr %r3,%r3 # char * - llgtr %r4,%r4 # void * - llgfr %r5,%r5 # size_t - jg sys_getxattr - -ENTRY(sys32_lgetxattr_wrapper) - llgtr %r2,%r2 # char * - llgtr %r3,%r3 # char * - llgtr %r4,%r4 # void * - llgfr %r5,%r5 # size_t - jg sys_lgetxattr - -ENTRY(sys32_fgetxattr_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # char * - llgtr %r4,%r4 # void * - llgfr %r5,%r5 # size_t - jg sys_fgetxattr - -ENTRY(sys32_listxattr_wrapper) - llgtr %r2,%r2 # char * - llgtr %r3,%r3 # char * - llgfr %r4,%r4 # size_t - jg sys_listxattr - -ENTRY(sys32_llistxattr_wrapper) - llgtr %r2,%r2 # char * - llgtr %r3,%r3 # char * - llgfr %r4,%r4 # size_t - jg sys_llistxattr - -ENTRY(sys32_flistxattr_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # char * - llgfr %r4,%r4 # size_t - jg sys_flistxattr - -ENTRY(sys32_removexattr_wrapper) - llgtr %r2,%r2 # char * - llgtr %r3,%r3 # char * - jg sys_removexattr - -ENTRY(sys32_lremovexattr_wrapper) - llgtr %r2,%r2 # char * - llgtr %r3,%r3 # char * - jg sys_lremovexattr - -ENTRY(sys32_fremovexattr_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # char * - jg sys_fremovexattr - -ENTRY(sys32_sched_setaffinity_wrapper) - lgfr %r2,%r2 # int - llgfr %r3,%r3 # unsigned int - llgtr %r4,%r4 # unsigned long * - jg compat_sys_sched_setaffinity - -ENTRY(sys32_sched_getaffinity_wrapper) - lgfr %r2,%r2 # int - llgfr %r3,%r3 # unsigned int - llgtr %r4,%r4 # unsigned long * - jg compat_sys_sched_getaffinity - -ENTRY(sys32_exit_group_wrapper) - lgfr %r2,%r2 # int - jg sys_exit_group # branch to system call - -ENTRY(sys32_set_tid_address_wrapper) - llgtr %r2,%r2 # int * - jg sys_set_tid_address # branch to system call - -ENTRY(sys_epoll_create_wrapper) - lgfr %r2,%r2 # int - jg sys_epoll_create # branch to system call - -ENTRY(sys_epoll_ctl_wrapper) - lgfr %r2,%r2 # int - lgfr %r3,%r3 # int - lgfr %r4,%r4 # int - llgtr %r5,%r5 # struct epoll_event * - jg sys_epoll_ctl # branch to system call - -ENTRY(sys_epoll_wait_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # struct epoll_event * - lgfr %r4,%r4 # int - lgfr %r5,%r5 # int - jg sys_epoll_wait # branch to system call - -ENTRY(sys32_lookup_dcookie_wrapper) - sllg %r2,%r2,32 # get high word of 64bit dcookie - or %r2,%r3 # get low word of 64bit dcookie - llgtr %r3,%r4 # char * - llgfr %r4,%r5 # size_t - jg sys_lookup_dcookie - -ENTRY(sys32_fadvise64_wrapper) - lgfr %r2,%r2 # int - sllg %r3,%r3,32 # get high word of 64bit loff_t - or %r3,%r4 # get low word of 64bit loff_t - llgfr %r4,%r5 # size_t (unsigned long) - lgfr %r5,%r6 # int - jg sys32_fadvise64 - -ENTRY(sys32_fadvise64_64_wrapper) - llgtr %r2,%r2 # struct fadvise64_64_args * - jg sys32_fadvise64_64 - -ENTRY(sys32_clock_settime_wrapper) - lgfr %r2,%r2 # clockid_t (int) - llgtr %r3,%r3 # struct compat_timespec * - jg compat_sys_clock_settime - -ENTRY(sys32_clock_gettime_wrapper) - lgfr %r2,%r2 # clockid_t (int) - llgtr %r3,%r3 # struct compat_timespec * - jg compat_sys_clock_gettime - -ENTRY(sys32_clock_getres_wrapper) - lgfr %r2,%r2 # clockid_t (int) - llgtr %r3,%r3 # struct compat_timespec * - jg compat_sys_clock_getres - -ENTRY(sys32_clock_nanosleep_wrapper) - lgfr %r2,%r2 # clockid_t (int) - lgfr %r3,%r3 # int - llgtr %r4,%r4 # struct compat_timespec * - llgtr %r5,%r5 # struct compat_timespec * - jg compat_sys_clock_nanosleep - -ENTRY(sys32_timer_create_wrapper) - lgfr %r2,%r2 # timer_t (int) - llgtr %r3,%r3 # struct compat_sigevent * - llgtr %r4,%r4 # timer_t * - jg compat_sys_timer_create - -ENTRY(sys32_timer_settime_wrapper) - lgfr %r2,%r2 # timer_t (int) - lgfr %r3,%r3 # int - llgtr %r4,%r4 # struct compat_itimerspec * - llgtr %r5,%r5 # struct compat_itimerspec * - jg compat_sys_timer_settime - -ENTRY(sys32_timer_gettime_wrapper) - lgfr %r2,%r2 # timer_t (int) - llgtr %r3,%r3 # struct compat_itimerspec * - jg compat_sys_timer_gettime - -ENTRY(sys32_timer_getoverrun_wrapper) - lgfr %r2,%r2 # timer_t (int) - jg sys_timer_getoverrun - -ENTRY(sys32_timer_delete_wrapper) - lgfr %r2,%r2 # timer_t (int) - jg sys_timer_delete - -ENTRY(sys32_io_setup_wrapper) - llgfr %r2,%r2 # unsigned int - llgtr %r3,%r3 # u32 * - jg compat_sys_io_setup - -ENTRY(sys32_io_destroy_wrapper) - llgfr %r2,%r2 # (aio_context_t) u32 - jg sys_io_destroy - -ENTRY(sys32_io_getevents_wrapper) - llgfr %r2,%r2 # (aio_context_t) u32 - lgfr %r3,%r3 # long - lgfr %r4,%r4 # long - llgtr %r5,%r5 # struct io_event * - llgtr %r6,%r6 # struct compat_timespec * - jg compat_sys_io_getevents - -ENTRY(sys32_io_submit_wrapper) - llgfr %r2,%r2 # (aio_context_t) u32 - lgfr %r3,%r3 # long - llgtr %r4,%r4 # struct iocb ** - jg compat_sys_io_submit - -ENTRY(sys32_io_cancel_wrapper) - llgfr %r2,%r2 # (aio_context_t) u32 - llgtr %r3,%r3 # struct iocb * - llgtr %r4,%r4 # struct io_event * - jg sys_io_cancel - -ENTRY(compat_sys_statfs64_wrapper) - llgtr %r2,%r2 # const char * - llgfr %r3,%r3 # compat_size_t - llgtr %r4,%r4 # struct compat_statfs64 * - jg compat_sys_statfs64 - -ENTRY(compat_sys_fstatfs64_wrapper) - llgfr %r2,%r2 # unsigned int fd - llgfr %r3,%r3 # compat_size_t - llgtr %r4,%r4 # struct compat_statfs64 * - jg compat_sys_fstatfs64 - -ENTRY(compat_sys_mq_open_wrapper) - llgtr %r2,%r2 # const char * - lgfr %r3,%r3 # int - llgfr %r4,%r4 # mode_t - llgtr %r5,%r5 # struct compat_mq_attr * - jg compat_sys_mq_open - -ENTRY(sys32_mq_unlink_wrapper) - llgtr %r2,%r2 # const char * - jg sys_mq_unlink - -ENTRY(compat_sys_mq_timedsend_wrapper) - lgfr %r2,%r2 # mqd_t - llgtr %r3,%r3 # const char * - llgfr %r4,%r4 # size_t - llgfr %r5,%r5 # unsigned int - llgtr %r6,%r6 # const struct compat_timespec * - jg compat_sys_mq_timedsend - -ENTRY(compat_sys_mq_timedreceive_wrapper) - lgfr %r2,%r2 # mqd_t - llgtr %r3,%r3 # char * - llgfr %r4,%r4 # size_t - llgtr %r5,%r5 # unsigned int * - llgtr %r6,%r6 # const struct compat_timespec * - jg compat_sys_mq_timedreceive - -ENTRY(compat_sys_mq_notify_wrapper) - lgfr %r2,%r2 # mqd_t - llgtr %r3,%r3 # struct compat_sigevent * - jg compat_sys_mq_notify - -ENTRY(compat_sys_mq_getsetattr_wrapper) - lgfr %r2,%r2 # mqd_t - llgtr %r3,%r3 # struct compat_mq_attr * - llgtr %r4,%r4 # struct compat_mq_attr * - jg compat_sys_mq_getsetattr - -ENTRY(compat_sys_add_key_wrapper) - llgtr %r2,%r2 # const char * - llgtr %r3,%r3 # const char * - llgtr %r4,%r4 # const void * - llgfr %r5,%r5 # size_t - llgfr %r6,%r6 # (key_serial_t) u32 - jg sys_add_key - -ENTRY(compat_sys_request_key_wrapper) - llgtr %r2,%r2 # const char * - llgtr %r3,%r3 # const char * - llgtr %r4,%r4 # const void * - llgfr %r5,%r5 # (key_serial_t) u32 - jg sys_request_key - -ENTRY(sys32_remap_file_pages_wrapper) - llgfr %r2,%r2 # unsigned long - llgfr %r3,%r3 # unsigned long - llgfr %r4,%r4 # unsigned long - llgfr %r5,%r5 # unsigned long - llgfr %r6,%r6 # unsigned long - jg sys_remap_file_pages - -ENTRY(compat_sys_waitid_wrapper) - lgfr %r2,%r2 # int - lgfr %r3,%r3 # pid_t - llgtr %r4,%r4 # siginfo_emu31_t * - lgfr %r5,%r5 # int - llgtr %r6,%r6 # struct rusage_emu31 * - jg compat_sys_waitid - -ENTRY(compat_sys_kexec_load_wrapper) - llgfr %r2,%r2 # unsigned long - llgfr %r3,%r3 # unsigned long - llgtr %r4,%r4 # struct kexec_segment * - llgfr %r5,%r5 # unsigned long - jg compat_sys_kexec_load - -ENTRY(sys_ioprio_set_wrapper) - lgfr %r2,%r2 # int - lgfr %r3,%r3 # int - lgfr %r4,%r4 # int - jg sys_ioprio_set - -ENTRY(sys_ioprio_get_wrapper) - lgfr %r2,%r2 # int - lgfr %r3,%r3 # int - jg sys_ioprio_get - -ENTRY(sys_inotify_add_watch_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # const char * - llgfr %r4,%r4 # u32 - jg sys_inotify_add_watch - -ENTRY(sys_inotify_rm_watch_wrapper) - lgfr %r2,%r2 # int - llgfr %r3,%r3 # u32 - jg sys_inotify_rm_watch - -ENTRY(compat_sys_openat_wrapper) - llgfr %r2,%r2 # unsigned int - llgtr %r3,%r3 # const char * - lgfr %r4,%r4 # int - lgfr %r5,%r5 # int - jg compat_sys_openat - -ENTRY(sys_mkdirat_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # const char * - lgfr %r4,%r4 # int - jg sys_mkdirat - -ENTRY(sys_mknodat_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # const char * - lgfr %r4,%r4 # int - llgfr %r5,%r5 # unsigned int - jg sys_mknodat - -ENTRY(sys_fchownat_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # const char * - llgfr %r4,%r4 # uid_t - llgfr %r5,%r5 # gid_t - lgfr %r6,%r6 # int - jg sys_fchownat - -ENTRY(compat_sys_futimesat_wrapper) - llgfr %r2,%r2 # unsigned int - llgtr %r3,%r3 # char * - llgtr %r4,%r4 # struct timeval * - jg compat_sys_futimesat - -ENTRY(sys32_fstatat64_wrapper) - llgfr %r2,%r2 # unsigned int - llgtr %r3,%r3 # char * - llgtr %r4,%r4 # struct stat64 * - lgfr %r5,%r5 # int - jg sys32_fstatat64 - -ENTRY(sys_unlinkat_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # const char * - lgfr %r4,%r4 # int - jg sys_unlinkat - -ENTRY(sys_renameat_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # const char * - lgfr %r4,%r4 # int - llgtr %r5,%r5 # const char * - jg sys_renameat - -ENTRY(sys_linkat_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # const char * - lgfr %r4,%r4 # int - llgtr %r5,%r5 # const char * - lgfr %r6,%r6 # int - jg sys_linkat - -ENTRY(sys_symlinkat_wrapper) - llgtr %r2,%r2 # const char * - lgfr %r3,%r3 # int - llgtr %r4,%r4 # const char * - jg sys_symlinkat - -ENTRY(sys_readlinkat_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # const char * - llgtr %r4,%r4 # char * - lgfr %r5,%r5 # int - jg sys_readlinkat - -ENTRY(sys_fchmodat_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # const char * - llgfr %r4,%r4 # mode_t - jg sys_fchmodat - -ENTRY(sys_faccessat_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # const char * - lgfr %r4,%r4 # int - jg sys_faccessat - -ENTRY(compat_sys_pselect6_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # fd_set * - llgtr %r4,%r4 # fd_set * - llgtr %r5,%r5 # fd_set * - llgtr %r6,%r6 # struct timespec * - llgt %r0,164(%r15) # void * - stg %r0,160(%r15) - jg compat_sys_pselect6 - -ENTRY(compat_sys_ppoll_wrapper) - llgtr %r2,%r2 # struct pollfd * - llgfr %r3,%r3 # unsigned int - llgtr %r4,%r4 # struct timespec * - llgtr %r5,%r5 # const sigset_t * - llgfr %r6,%r6 # size_t - jg compat_sys_ppoll - -ENTRY(sys_unshare_wrapper) - llgfr %r2,%r2 # unsigned long - jg sys_unshare - -ENTRY(compat_sys_set_robust_list_wrapper) - llgtr %r2,%r2 # struct compat_robust_list_head * - llgfr %r3,%r3 # size_t - jg compat_sys_set_robust_list - -ENTRY(compat_sys_get_robust_list_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # compat_uptr_t_t * - llgtr %r4,%r4 # compat_size_t * - jg compat_sys_get_robust_list - -ENTRY(sys_splice_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # loff_t * - lgfr %r4,%r4 # int - llgtr %r5,%r5 # loff_t * - llgfr %r6,%r6 # size_t - llgf %r0,164(%r15) # unsigned int - stg %r0,160(%r15) - jg sys_splice - -ENTRY(sys_sync_file_range_wrapper) - lgfr %r2,%r2 # int - sllg %r3,%r3,32 # get high word of 64bit loff_t - or %r3,%r4 # get low word of 64bit loff_t - sllg %r4,%r5,32 # get high word of 64bit loff_t - or %r4,%r6 # get low word of 64bit loff_t - llgf %r5,164(%r15) # unsigned int - jg sys_sync_file_range - -ENTRY(sys_tee_wrapper) - lgfr %r2,%r2 # int - lgfr %r3,%r3 # int - llgfr %r4,%r4 # size_t - llgfr %r5,%r5 # unsigned int - jg sys_tee - -ENTRY(compat_sys_vmsplice_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # compat_iovec * - llgfr %r4,%r4 # unsigned int - llgfr %r5,%r5 # unsigned int - jg compat_sys_vmsplice - -ENTRY(sys_getcpu_wrapper) - llgtr %r2,%r2 # unsigned * - llgtr %r3,%r3 # unsigned * - llgtr %r4,%r4 # struct getcpu_cache * - jg sys_getcpu - -ENTRY(compat_sys_epoll_pwait_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # struct compat_epoll_event * - lgfr %r4,%r4 # int - lgfr %r5,%r5 # int - llgtr %r6,%r6 # compat_sigset_t * - llgf %r0,164(%r15) # compat_size_t - stg %r0,160(%r15) - jg compat_sys_epoll_pwait - -ENTRY(compat_sys_utimes_wrapper) - llgtr %r2,%r2 # char * - llgtr %r3,%r3 # struct compat_timeval * - jg compat_sys_utimes - -ENTRY(compat_sys_utimensat_wrapper) - llgfr %r2,%r2 # unsigned int - llgtr %r3,%r3 # char * - llgtr %r4,%r4 # struct compat_timespec * - lgfr %r5,%r5 # int - jg compat_sys_utimensat - -ENTRY(compat_sys_signalfd_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # compat_sigset_t * - llgfr %r4,%r4 # compat_size_t - jg compat_sys_signalfd - -ENTRY(sys_eventfd_wrapper) - llgfr %r2,%r2 # unsigned int - jg sys_eventfd - -ENTRY(sys_fallocate_wrapper) - lgfr %r2,%r2 # int - lgfr %r3,%r3 # int - sllg %r4,%r4,32 # get high word of 64bit loff_t - lr %r4,%r5 # get low word of 64bit loff_t - sllg %r5,%r6,32 # get high word of 64bit loff_t - l %r5,164(%r15) # get low word of 64bit loff_t - jg sys_fallocate - -ENTRY(sys_timerfd_create_wrapper) - lgfr %r2,%r2 # int - lgfr %r3,%r3 # int - jg sys_timerfd_create - -ENTRY(compat_sys_timerfd_settime_wrapper) - lgfr %r2,%r2 # int - lgfr %r3,%r3 # int - llgtr %r4,%r4 # struct compat_itimerspec * - llgtr %r5,%r5 # struct compat_itimerspec * - jg compat_sys_timerfd_settime - -ENTRY(compat_sys_timerfd_gettime_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # struct compat_itimerspec * - jg compat_sys_timerfd_gettime - -ENTRY(compat_sys_signalfd4_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # compat_sigset_t * - llgfr %r4,%r4 # compat_size_t - lgfr %r5,%r5 # int - jg compat_sys_signalfd4 - -ENTRY(sys_eventfd2_wrapper) - llgfr %r2,%r2 # unsigned int - lgfr %r3,%r3 # int - jg sys_eventfd2 - -ENTRY(sys_inotify_init1_wrapper) - lgfr %r2,%r2 # int - jg sys_inotify_init1 - -ENTRY(sys_pipe2_wrapper) - llgtr %r2,%r2 # u32 * - lgfr %r3,%r3 # int - jg sys_pipe2 # branch to system call - -ENTRY(sys_dup3_wrapper) - llgfr %r2,%r2 # unsigned int - llgfr %r3,%r3 # unsigned int - lgfr %r4,%r4 # int - jg sys_dup3 # branch to system call - -ENTRY(sys_epoll_create1_wrapper) - lgfr %r2,%r2 # int - jg sys_epoll_create1 # branch to system call - -ENTRY(sys32_readahead_wrapper) - lgfr %r2,%r2 # int - llgfr %r3,%r3 # u32 - llgfr %r4,%r4 # u32 - lgfr %r5,%r5 # s32 - jg sys32_readahead # branch to system call - -ENTRY(sys32_sendfile64_wrapper) - lgfr %r2,%r2 # int - lgfr %r3,%r3 # int - llgtr %r4,%r4 # compat_loff_t * - lgfr %r5,%r5 # s32 - jg sys32_sendfile64 # branch to system call - -ENTRY(sys_tkill_wrapper) - lgfr %r2,%r2 # pid_t - lgfr %r3,%r3 # int - jg sys_tkill # branch to system call - -ENTRY(sys_tgkill_wrapper) - lgfr %r2,%r2 # pid_t - lgfr %r3,%r3 # pid_t - lgfr %r4,%r4 # int - jg sys_tgkill # branch to system call - -ENTRY(compat_sys_keyctl_wrapper) - llgfr %r2,%r2 # u32 - llgfr %r3,%r3 # u32 - llgfr %r4,%r4 # u32 - llgfr %r5,%r5 # u32 - llgfr %r6,%r6 # u32 - jg compat_sys_keyctl # branch to system call - -ENTRY(compat_sys_preadv_wrapper) - llgfr %r2,%r2 # unsigned long - llgtr %r3,%r3 # compat_iovec * - llgfr %r4,%r4 # unsigned long - llgfr %r5,%r5 # u32 - llgfr %r6,%r6 # u32 - jg compat_sys_preadv # branch to system call - -ENTRY(compat_sys_pwritev_wrapper) - llgfr %r2,%r2 # unsigned long - llgtr %r3,%r3 # compat_iovec * - llgfr %r4,%r4 # unsigned long - llgfr %r5,%r5 # u32 - llgfr %r6,%r6 # u32 - jg compat_sys_pwritev # branch to system call - -ENTRY(compat_sys_rt_tgsigqueueinfo_wrapper) - lgfr %r2,%r2 # compat_pid_t - lgfr %r3,%r3 # compat_pid_t - lgfr %r4,%r4 # int - llgtr %r5,%r5 # struct compat_siginfo * - jg compat_sys_rt_tgsigqueueinfo_wrapper # branch to system call - -ENTRY(sys_perf_event_open_wrapper) - llgtr %r2,%r2 # const struct perf_event_attr * - lgfr %r3,%r3 # pid_t - lgfr %r4,%r4 # int - lgfr %r5,%r5 # int - llgfr %r6,%r6 # unsigned long - jg sys_perf_event_open # branch to system call - -ENTRY(sys_clone_wrapper) - llgfr %r2,%r2 # unsigned long - llgfr %r3,%r3 # unsigned long - llgtr %r4,%r4 # int * - llgtr %r5,%r5 # int * - jg sys_clone # branch to system call - -ENTRY(sys32_execve_wrapper) - llgtr %r2,%r2 # char * - llgtr %r3,%r3 # compat_uptr_t * - llgtr %r4,%r4 # compat_uptr_t * - jg sys32_execve # branch to system call - -ENTRY(sys_fanotify_init_wrapper) - llgfr %r2,%r2 # unsigned int - llgfr %r3,%r3 # unsigned int - jg sys_fanotify_init # branch to system call - -ENTRY(sys_fanotify_mark_wrapper) - lgfr %r2,%r2 # int - llgfr %r3,%r3 # unsigned int - sllg %r4,%r4,32 # get high word of 64bit mask - lr %r4,%r5 # get low word of 64bit mask - llgfr %r5,%r6 # unsigned int - llgt %r6,164(%r15) # char * - jg sys_fanotify_mark # branch to system call - -ENTRY(sys_prlimit64_wrapper) - lgfr %r2,%r2 # pid_t - llgfr %r3,%r3 # unsigned int - llgtr %r4,%r4 # const struct rlimit64 __user * - llgtr %r5,%r5 # struct rlimit64 __user * - jg sys_prlimit64 # branch to system call - -ENTRY(sys_name_to_handle_at_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # const char __user * - llgtr %r4,%r4 # struct file_handle __user * - llgtr %r5,%r5 # int __user * - lgfr %r6,%r6 # int - jg sys_name_to_handle_at - -ENTRY(compat_sys_open_by_handle_at_wrapper) - lgfr %r2,%r2 # int - llgtr %r3,%r3 # struct file_handle __user * - lgfr %r4,%r4 # int - jg compat_sys_open_by_handle_at - -ENTRY(compat_sys_clock_adjtime_wrapper) - lgfr %r2,%r2 # clockid_t (int) - llgtr %r3,%r3 # struct compat_timex __user * - jg compat_sys_clock_adjtime - -ENTRY(sys_syncfs_wrapper) - lgfr %r2,%r2 # int - jg sys_syncfs - -ENTRY(sys_setns_wrapper) - lgfr %r2,%r2 # int - lgfr %r3,%r3 # int - jg sys_setns - -ENTRY(compat_sys_process_vm_readv_wrapper) - lgfr %r2,%r2 # compat_pid_t - llgtr %r3,%r3 # struct compat_iovec __user * - llgfr %r4,%r4 # unsigned long - llgtr %r5,%r5 # struct compat_iovec __user * - llgfr %r6,%r6 # unsigned long - llgf %r0,164(%r15) # unsigned long - stg %r0,160(%r15) - jg sys_process_vm_readv - -ENTRY(compat_sys_process_vm_writev_wrapper) - lgfr %r2,%r2 # compat_pid_t - llgtr %r3,%r3 # struct compat_iovec __user * - llgfr %r4,%r4 # unsigned long - llgtr %r5,%r5 # struct compat_iovec __user * - llgfr %r6,%r6 # unsigned long - llgf %r0,164(%r15) # unsigned long - stg %r0,160(%r15) - jg sys_process_vm_writev diff --git a/ANDROID_3.4.5/arch/s390/kernel/cpcmd.c b/ANDROID_3.4.5/arch/s390/kernel/cpcmd.c deleted file mode 100644 index e3dd886e..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/cpcmd.c +++ /dev/null @@ -1,125 +0,0 @@ -/* - * arch/s390/kernel/cpcmd.c - * - * S390 version - * Copyright IBM Corp. 1999,2007 - * Author(s): Martin Schwidefsky (schwidefsky@de.ibm.com), - * Christian Borntraeger (cborntra@de.ibm.com), - */ - -#define KMSG_COMPONENT "cpcmd" -#define pr_fmt(fmt) KMSG_COMPONENT ": " fmt - -#include <linux/kernel.h> -#include <linux/module.h> -#include <linux/slab.h> -#include <linux/spinlock.h> -#include <linux/stddef.h> -#include <linux/string.h> -#include <asm/ebcdic.h> -#include <asm/cpcmd.h> -#include <asm/io.h> - -static DEFINE_SPINLOCK(cpcmd_lock); -static char cpcmd_buf[241]; - -static int diag8_noresponse(int cmdlen) -{ - register unsigned long reg2 asm ("2") = (addr_t) cpcmd_buf; - register unsigned long reg3 asm ("3") = cmdlen; - - asm volatile( -#ifndef CONFIG_64BIT - " diag %1,%0,0x8\n" -#else /* CONFIG_64BIT */ - " sam31\n" - " diag %1,%0,0x8\n" - " sam64\n" -#endif /* CONFIG_64BIT */ - : "+d" (reg3) : "d" (reg2) : "cc"); - return reg3; -} - -static int diag8_response(int cmdlen, char *response, int *rlen) -{ - register unsigned long reg2 asm ("2") = (addr_t) cpcmd_buf; - register unsigned long reg3 asm ("3") = (addr_t) response; - register unsigned long reg4 asm ("4") = cmdlen | 0x40000000L; - register unsigned long reg5 asm ("5") = *rlen; - - asm volatile( -#ifndef CONFIG_64BIT - " diag %2,%0,0x8\n" - " brc 8,1f\n" - " ar %1,%4\n" -#else /* CONFIG_64BIT */ - " sam31\n" - " diag %2,%0,0x8\n" - " sam64\n" - " brc 8,1f\n" - " agr %1,%4\n" -#endif /* CONFIG_64BIT */ - "1:\n" - : "+d" (reg4), "+d" (reg5) - : "d" (reg2), "d" (reg3), "d" (*rlen) : "cc"); - *rlen = reg5; - return reg4; -} - -/* - * __cpcmd has some restrictions over cpcmd - * - the response buffer must reside below 2GB (if any) - * - __cpcmd is unlocked and therefore not SMP-safe - */ -int __cpcmd(const char *cmd, char *response, int rlen, int *response_code) -{ - int cmdlen; - int rc; - int response_len; - - cmdlen = strlen(cmd); - BUG_ON(cmdlen > 240); - memcpy(cpcmd_buf, cmd, cmdlen); - ASCEBC(cpcmd_buf, cmdlen); - - if (response) { - memset(response, 0, rlen); - response_len = rlen; - rc = diag8_response(cmdlen, response, &rlen); - EBCASC(response, response_len); - } else { - rc = diag8_noresponse(cmdlen); - } - if (response_code) - *response_code = rc; - return rlen; -} -EXPORT_SYMBOL(__cpcmd); - -int cpcmd(const char *cmd, char *response, int rlen, int *response_code) -{ - char *lowbuf; - int len; - unsigned long flags; - - if ((virt_to_phys(response) != (unsigned long) response) || - (((unsigned long)response + rlen) >> 31)) { - lowbuf = kmalloc(rlen, GFP_KERNEL | GFP_DMA); - if (!lowbuf) { - pr_warning("The cpcmd kernel function failed to " - "allocate a response buffer\n"); - return -ENOMEM; - } - spin_lock_irqsave(&cpcmd_lock, flags); - len = __cpcmd(cmd, lowbuf, rlen, response_code); - spin_unlock_irqrestore(&cpcmd_lock, flags); - memcpy(response, lowbuf, rlen); - kfree(lowbuf); - } else { - spin_lock_irqsave(&cpcmd_lock, flags); - len = __cpcmd(cmd, response, rlen, response_code); - spin_unlock_irqrestore(&cpcmd_lock, flags); - } - return len; -} -EXPORT_SYMBOL(cpcmd); diff --git a/ANDROID_3.4.5/arch/s390/kernel/crash.c b/ANDROID_3.4.5/arch/s390/kernel/crash.c deleted file mode 100644 index 8cc7c9fa..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/crash.c +++ /dev/null @@ -1,16 +0,0 @@ -/* - * arch/s390/kernel/crash.c - * - * (C) Copyright IBM Corp. 2005 - * - * Author(s): Heiko Carstens <heiko.carstens@de.ibm.com> - * - */ - -#include <linux/threads.h> -#include <linux/kexec.h> -#include <linux/reboot.h> - -void machine_crash_shutdown(struct pt_regs *regs) -{ -} diff --git a/ANDROID_3.4.5/arch/s390/kernel/crash_dump.c b/ANDROID_3.4.5/arch/s390/kernel/crash_dump.c deleted file mode 100644 index cc1172b2..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/crash_dump.c +++ /dev/null @@ -1,442 +0,0 @@ -/* - * S390 kdump implementation - * - * Copyright IBM Corp. 2011 - * Author(s): Michael Holzheu <holzheu@linux.vnet.ibm.com> - */ - -#include <linux/crash_dump.h> -#include <asm/lowcore.h> -#include <linux/kernel.h> -#include <linux/module.h> -#include <linux/gfp.h> -#include <linux/slab.h> -#include <linux/bootmem.h> -#include <linux/elf.h> -#include <asm/ipl.h> -#include <asm/os_info.h> - -#define PTR_ADD(x, y) (((char *) (x)) + ((unsigned long) (y))) -#define PTR_SUB(x, y) (((char *) (x)) - ((unsigned long) (y))) -#define PTR_DIFF(x, y) ((unsigned long)(((char *) (x)) - ((unsigned long) (y)))) - -/* - * Copy one page from "oldmem" - * - * For the kdump reserved memory this functions performs a swap operation: - * - [OLDMEM_BASE - OLDMEM_BASE + OLDMEM_SIZE] is mapped to [0 - OLDMEM_SIZE]. - * - [0 - OLDMEM_SIZE] is mapped to [OLDMEM_BASE - OLDMEM_BASE + OLDMEM_SIZE] - */ -ssize_t copy_oldmem_page(unsigned long pfn, char *buf, - size_t csize, unsigned long offset, int userbuf) -{ - unsigned long src; - - if (!csize) - return 0; - - src = (pfn << PAGE_SHIFT) + offset; - if (src < OLDMEM_SIZE) - src += OLDMEM_BASE; - else if (src > OLDMEM_BASE && - src < OLDMEM_BASE + OLDMEM_SIZE) - src -= OLDMEM_BASE; - if (userbuf) - copy_to_user_real((void __force __user *) buf, (void *) src, - csize); - else - memcpy_real(buf, (void *) src, csize); - return csize; -} - -/* - * Copy memory from old kernel - */ -int copy_from_oldmem(void *dest, void *src, size_t count) -{ - unsigned long copied = 0; - int rc; - - if ((unsigned long) src < OLDMEM_SIZE) { - copied = min(count, OLDMEM_SIZE - (unsigned long) src); - rc = memcpy_real(dest, src + OLDMEM_BASE, copied); - if (rc) - return rc; - } - return memcpy_real(dest + copied, src + copied, count - copied); -} - -/* - * Alloc memory and panic in case of ENOMEM - */ -static void *kzalloc_panic(int len) -{ - void *rc; - - rc = kzalloc(len, GFP_KERNEL); - if (!rc) - panic("s390 kdump kzalloc (%d) failed", len); - return rc; -} - -/* - * Get memory layout and create hole for oldmem - */ -static struct mem_chunk *get_memory_layout(void) -{ - struct mem_chunk *chunk_array; - - chunk_array = kzalloc_panic(MEMORY_CHUNKS * sizeof(struct mem_chunk)); - detect_memory_layout(chunk_array); - create_mem_hole(chunk_array, OLDMEM_BASE, OLDMEM_SIZE, CHUNK_CRASHK); - return chunk_array; -} - -/* - * Initialize ELF note - */ -static void *nt_init(void *buf, Elf64_Word type, void *desc, int d_len, - const char *name) -{ - Elf64_Nhdr *note; - u64 len; - - note = (Elf64_Nhdr *)buf; - note->n_namesz = strlen(name) + 1; - note->n_descsz = d_len; - note->n_type = type; - len = sizeof(Elf64_Nhdr); - - memcpy(buf + len, name, note->n_namesz); - len = roundup(len + note->n_namesz, 4); - - memcpy(buf + len, desc, note->n_descsz); - len = roundup(len + note->n_descsz, 4); - - return PTR_ADD(buf, len); -} - -/* - * Initialize prstatus note - */ -static void *nt_prstatus(void *ptr, struct save_area *sa) -{ - struct elf_prstatus nt_prstatus; - static int cpu_nr = 1; - - memset(&nt_prstatus, 0, sizeof(nt_prstatus)); - memcpy(&nt_prstatus.pr_reg.gprs, sa->gp_regs, sizeof(sa->gp_regs)); - memcpy(&nt_prstatus.pr_reg.psw, sa->psw, sizeof(sa->psw)); - memcpy(&nt_prstatus.pr_reg.acrs, sa->acc_regs, sizeof(sa->acc_regs)); - nt_prstatus.pr_pid = cpu_nr; - cpu_nr++; - - return nt_init(ptr, NT_PRSTATUS, &nt_prstatus, sizeof(nt_prstatus), - "CORE"); -} - -/* - * Initialize fpregset (floating point) note - */ -static void *nt_fpregset(void *ptr, struct save_area *sa) -{ - elf_fpregset_t nt_fpregset; - - memset(&nt_fpregset, 0, sizeof(nt_fpregset)); - memcpy(&nt_fpregset.fpc, &sa->fp_ctrl_reg, sizeof(sa->fp_ctrl_reg)); - memcpy(&nt_fpregset.fprs, &sa->fp_regs, sizeof(sa->fp_regs)); - - return nt_init(ptr, NT_PRFPREG, &nt_fpregset, sizeof(nt_fpregset), - "CORE"); -} - -/* - * Initialize timer note - */ -static void *nt_s390_timer(void *ptr, struct save_area *sa) -{ - return nt_init(ptr, NT_S390_TIMER, &sa->timer, sizeof(sa->timer), - KEXEC_CORE_NOTE_NAME); -} - -/* - * Initialize TOD clock comparator note - */ -static void *nt_s390_tod_cmp(void *ptr, struct save_area *sa) -{ - return nt_init(ptr, NT_S390_TODCMP, &sa->clk_cmp, - sizeof(sa->clk_cmp), KEXEC_CORE_NOTE_NAME); -} - -/* - * Initialize TOD programmable register note - */ -static void *nt_s390_tod_preg(void *ptr, struct save_area *sa) -{ - return nt_init(ptr, NT_S390_TODPREG, &sa->tod_reg, - sizeof(sa->tod_reg), KEXEC_CORE_NOTE_NAME); -} - -/* - * Initialize control register note - */ -static void *nt_s390_ctrs(void *ptr, struct save_area *sa) -{ - return nt_init(ptr, NT_S390_CTRS, &sa->ctrl_regs, - sizeof(sa->ctrl_regs), KEXEC_CORE_NOTE_NAME); -} - -/* - * Initialize prefix register note - */ -static void *nt_s390_prefix(void *ptr, struct save_area *sa) -{ - return nt_init(ptr, NT_S390_PREFIX, &sa->pref_reg, - sizeof(sa->pref_reg), KEXEC_CORE_NOTE_NAME); -} - -/* - * Fill ELF notes for one CPU with save area registers - */ -void *fill_cpu_elf_notes(void *ptr, struct save_area *sa) -{ - ptr = nt_prstatus(ptr, sa); - ptr = nt_fpregset(ptr, sa); - ptr = nt_s390_timer(ptr, sa); - ptr = nt_s390_tod_cmp(ptr, sa); - ptr = nt_s390_tod_preg(ptr, sa); - ptr = nt_s390_ctrs(ptr, sa); - ptr = nt_s390_prefix(ptr, sa); - return ptr; -} - -/* - * Initialize prpsinfo note (new kernel) - */ -static void *nt_prpsinfo(void *ptr) -{ - struct elf_prpsinfo prpsinfo; - - memset(&prpsinfo, 0, sizeof(prpsinfo)); - prpsinfo.pr_sname = 'R'; - strcpy(prpsinfo.pr_fname, "vmlinux"); - return nt_init(ptr, NT_PRPSINFO, &prpsinfo, sizeof(prpsinfo), - KEXEC_CORE_NOTE_NAME); -} - -/* - * Get vmcoreinfo using lowcore->vmcore_info (new kernel) - */ -static void *get_vmcoreinfo_old(unsigned long *size) -{ - char nt_name[11], *vmcoreinfo; - Elf64_Nhdr note; - void *addr; - - if (copy_from_oldmem(&addr, &S390_lowcore.vmcore_info, sizeof(addr))) - return NULL; - memset(nt_name, 0, sizeof(nt_name)); - if (copy_from_oldmem(¬e, addr, sizeof(note))) - return NULL; - if (copy_from_oldmem(nt_name, addr + sizeof(note), sizeof(nt_name) - 1)) - return NULL; - if (strcmp(nt_name, "VMCOREINFO") != 0) - return NULL; - vmcoreinfo = kzalloc_panic(note.n_descsz); - if (copy_from_oldmem(vmcoreinfo, addr + 24, note.n_descsz)) - return NULL; - *size = note.n_descsz; - return vmcoreinfo; -} - -/* - * Initialize vmcoreinfo note (new kernel) - */ -static void *nt_vmcoreinfo(void *ptr) -{ - unsigned long size; - void *vmcoreinfo; - - vmcoreinfo = os_info_old_entry(OS_INFO_VMCOREINFO, &size); - if (!vmcoreinfo) - vmcoreinfo = get_vmcoreinfo_old(&size); - if (!vmcoreinfo) - return ptr; - return nt_init(ptr, 0, vmcoreinfo, size, "VMCOREINFO"); -} - -/* - * Initialize ELF header (new kernel) - */ -static void *ehdr_init(Elf64_Ehdr *ehdr, int mem_chunk_cnt) -{ - memset(ehdr, 0, sizeof(*ehdr)); - memcpy(ehdr->e_ident, ELFMAG, SELFMAG); - ehdr->e_ident[EI_CLASS] = ELFCLASS64; - ehdr->e_ident[EI_DATA] = ELFDATA2MSB; - ehdr->e_ident[EI_VERSION] = EV_CURRENT; - memset(ehdr->e_ident + EI_PAD, 0, EI_NIDENT - EI_PAD); - ehdr->e_type = ET_CORE; - ehdr->e_machine = EM_S390; - ehdr->e_version = EV_CURRENT; - ehdr->e_phoff = sizeof(Elf64_Ehdr); - ehdr->e_ehsize = sizeof(Elf64_Ehdr); - ehdr->e_phentsize = sizeof(Elf64_Phdr); - ehdr->e_phnum = mem_chunk_cnt + 1; - return ehdr + 1; -} - -/* - * Return CPU count for ELF header (new kernel) - */ -static int get_cpu_cnt(void) -{ - int i, cpus = 0; - - for (i = 0; zfcpdump_save_areas[i]; i++) { - if (zfcpdump_save_areas[i]->pref_reg == 0) - continue; - cpus++; - } - return cpus; -} - -/* - * Return memory chunk count for ELF header (new kernel) - */ -static int get_mem_chunk_cnt(void) -{ - struct mem_chunk *chunk_array, *mem_chunk; - int i, cnt = 0; - - chunk_array = get_memory_layout(); - for (i = 0; i < MEMORY_CHUNKS; i++) { - mem_chunk = &chunk_array[i]; - if (chunk_array[i].type != CHUNK_READ_WRITE && - chunk_array[i].type != CHUNK_READ_ONLY) - continue; - if (mem_chunk->size == 0) - continue; - cnt++; - } - kfree(chunk_array); - return cnt; -} - -/* - * Relocate pointer in order to allow vmcore code access the data - */ -static inline unsigned long relocate(unsigned long addr) -{ - return OLDMEM_BASE + addr; -} - -/* - * Initialize ELF loads (new kernel) - */ -static int loads_init(Elf64_Phdr *phdr, u64 loads_offset) -{ - struct mem_chunk *chunk_array, *mem_chunk; - int i; - - chunk_array = get_memory_layout(); - for (i = 0; i < MEMORY_CHUNKS; i++) { - mem_chunk = &chunk_array[i]; - if (mem_chunk->size == 0) - break; - if (chunk_array[i].type != CHUNK_READ_WRITE && - chunk_array[i].type != CHUNK_READ_ONLY) - continue; - else - phdr->p_filesz = mem_chunk->size; - phdr->p_type = PT_LOAD; - phdr->p_offset = mem_chunk->addr; - phdr->p_vaddr = mem_chunk->addr; - phdr->p_paddr = mem_chunk->addr; - phdr->p_memsz = mem_chunk->size; - phdr->p_flags = PF_R | PF_W | PF_X; - phdr->p_align = PAGE_SIZE; - phdr++; - } - kfree(chunk_array); - return i; -} - -/* - * Initialize notes (new kernel) - */ -static void *notes_init(Elf64_Phdr *phdr, void *ptr, u64 notes_offset) -{ - struct save_area *sa; - void *ptr_start = ptr; - int i; - - ptr = nt_prpsinfo(ptr); - - for (i = 0; zfcpdump_save_areas[i]; i++) { - sa = zfcpdump_save_areas[i]; - if (sa->pref_reg == 0) - continue; - ptr = fill_cpu_elf_notes(ptr, sa); - } - ptr = nt_vmcoreinfo(ptr); - memset(phdr, 0, sizeof(*phdr)); - phdr->p_type = PT_NOTE; - phdr->p_offset = relocate(notes_offset); - phdr->p_filesz = (unsigned long) PTR_SUB(ptr, ptr_start); - phdr->p_memsz = phdr->p_filesz; - return ptr; -} - -/* - * Create ELF core header (new kernel) - */ -static void s390_elf_corehdr_create(char **elfcorebuf, size_t *elfcorebuf_sz) -{ - Elf64_Phdr *phdr_notes, *phdr_loads; - int mem_chunk_cnt; - void *ptr, *hdr; - u32 alloc_size; - u64 hdr_off; - - mem_chunk_cnt = get_mem_chunk_cnt(); - - alloc_size = 0x1000 + get_cpu_cnt() * 0x300 + - mem_chunk_cnt * sizeof(Elf64_Phdr); - hdr = kzalloc_panic(alloc_size); - /* Init elf header */ - ptr = ehdr_init(hdr, mem_chunk_cnt); - /* Init program headers */ - phdr_notes = ptr; - ptr = PTR_ADD(ptr, sizeof(Elf64_Phdr)); - phdr_loads = ptr; - ptr = PTR_ADD(ptr, sizeof(Elf64_Phdr) * mem_chunk_cnt); - /* Init notes */ - hdr_off = PTR_DIFF(ptr, hdr); - ptr = notes_init(phdr_notes, ptr, ((unsigned long) hdr) + hdr_off); - /* Init loads */ - hdr_off = PTR_DIFF(ptr, hdr); - loads_init(phdr_loads, ((unsigned long) hdr) + hdr_off); - *elfcorebuf_sz = hdr_off; - *elfcorebuf = (void *) relocate((unsigned long) hdr); - BUG_ON(*elfcorebuf_sz > alloc_size); -} - -/* - * Create kdump ELF core header in new kernel, if it has not been passed via - * the "elfcorehdr" kernel parameter - */ -static int setup_kdump_elfcorehdr(void) -{ - size_t elfcorebuf_sz; - char *elfcorebuf; - - if (!OLDMEM_BASE || is_kdump_kernel()) - return -EINVAL; - s390_elf_corehdr_create(&elfcorebuf, &elfcorebuf_sz); - elfcorehdr_addr = (unsigned long long) elfcorebuf; - elfcorehdr_size = elfcorebuf_sz; - return 0; -} - -subsys_initcall(setup_kdump_elfcorehdr); diff --git a/ANDROID_3.4.5/arch/s390/kernel/debug.c b/ANDROID_3.4.5/arch/s390/kernel/debug.c deleted file mode 100644 index 19e5e9eb..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/debug.c +++ /dev/null @@ -1,1566 +0,0 @@ -/* - * arch/s390/kernel/debug.c - * S/390 debug facility - * - * Copyright IBM Corp. 1999, 2012 - * - * Author(s): Michael Holzheu (holzheu@de.ibm.com), - * Holger Smolinski (Holger.Smolinski@de.ibm.com) - * - * Bugreports to: <Linux390@de.ibm.com> - */ - -#define KMSG_COMPONENT "s390dbf" -#define pr_fmt(fmt) KMSG_COMPONENT ": " fmt - -#include <linux/stddef.h> -#include <linux/kernel.h> -#include <linux/errno.h> -#include <linux/slab.h> -#include <linux/ctype.h> -#include <linux/string.h> -#include <linux/sysctl.h> -#include <asm/uaccess.h> -#include <linux/module.h> -#include <linux/init.h> -#include <linux/fs.h> -#include <linux/debugfs.h> - -#include <asm/debug.h> - -#define DEBUG_PROLOG_ENTRY -1 - -#define ALL_AREAS 0 /* copy all debug areas */ -#define NO_AREAS 1 /* copy no debug areas */ - -/* typedefs */ - -typedef struct file_private_info { - loff_t offset; /* offset of last read in file */ - int act_area; /* number of last formated area */ - int act_page; /* act page in given area */ - int act_entry; /* last formated entry (offset */ - /* relative to beginning of last */ - /* formated page) */ - size_t act_entry_offset; /* up to this offset we copied */ - /* in last read the last formated */ - /* entry to userland */ - char temp_buf[2048]; /* buffer for output */ - debug_info_t *debug_info_org; /* original debug information */ - debug_info_t *debug_info_snap; /* snapshot of debug information */ - struct debug_view *view; /* used view of debug info */ -} file_private_info_t; - -typedef struct -{ - char *string; - /* - * This assumes that all args are converted into longs - * on L/390 this is the case for all types of parameter - * except of floats, and long long (32 bit) - * - */ - long args[0]; -} debug_sprintf_entry_t; - - -/* internal function prototyes */ - -static int debug_init(void); -static ssize_t debug_output(struct file *file, char __user *user_buf, - size_t user_len, loff_t * offset); -static ssize_t debug_input(struct file *file, const char __user *user_buf, - size_t user_len, loff_t * offset); -static int debug_open(struct inode *inode, struct file *file); -static int debug_close(struct inode *inode, struct file *file); -static debug_info_t *debug_info_create(const char *name, int pages_per_area, - int nr_areas, int buf_size, umode_t mode); -static void debug_info_get(debug_info_t *); -static void debug_info_put(debug_info_t *); -static int debug_prolog_level_fn(debug_info_t * id, - struct debug_view *view, char *out_buf); -static int debug_input_level_fn(debug_info_t * id, struct debug_view *view, - struct file *file, const char __user *user_buf, - size_t user_buf_size, loff_t * offset); -static int debug_prolog_pages_fn(debug_info_t * id, - struct debug_view *view, char *out_buf); -static int debug_input_pages_fn(debug_info_t * id, struct debug_view *view, - struct file *file, const char __user *user_buf, - size_t user_buf_size, loff_t * offset); -static int debug_input_flush_fn(debug_info_t * id, struct debug_view *view, - struct file *file, const char __user *user_buf, - size_t user_buf_size, loff_t * offset); -static int debug_hex_ascii_format_fn(debug_info_t * id, struct debug_view *view, - char *out_buf, const char *in_buf); -static int debug_raw_format_fn(debug_info_t * id, - struct debug_view *view, char *out_buf, - const char *in_buf); -static int debug_raw_header_fn(debug_info_t * id, struct debug_view *view, - int area, debug_entry_t * entry, char *out_buf); - -static int debug_sprintf_format_fn(debug_info_t * id, struct debug_view *view, - char *out_buf, debug_sprintf_entry_t *curr_event); - -/* globals */ - -struct debug_view debug_raw_view = { - "raw", - NULL, - &debug_raw_header_fn, - &debug_raw_format_fn, - NULL, - NULL -}; - -struct debug_view debug_hex_ascii_view = { - "hex_ascii", - NULL, - &debug_dflt_header_fn, - &debug_hex_ascii_format_fn, - NULL, - NULL -}; - -static struct debug_view debug_level_view = { - "level", - &debug_prolog_level_fn, - NULL, - NULL, - &debug_input_level_fn, - NULL -}; - -static struct debug_view debug_pages_view = { - "pages", - &debug_prolog_pages_fn, - NULL, - NULL, - &debug_input_pages_fn, - NULL -}; - -static struct debug_view debug_flush_view = { - "flush", - NULL, - NULL, - NULL, - &debug_input_flush_fn, - NULL -}; - -struct debug_view debug_sprintf_view = { - "sprintf", - NULL, - &debug_dflt_header_fn, - (debug_format_proc_t*)&debug_sprintf_format_fn, - NULL, - NULL -}; - -/* used by dump analysis tools to determine version of debug feature */ -static unsigned int __used debug_feature_version = __DEBUG_FEATURE_VERSION; - -/* static globals */ - -static debug_info_t *debug_area_first = NULL; -static debug_info_t *debug_area_last = NULL; -static DEFINE_MUTEX(debug_mutex); - -static int initialized; -static int debug_critical; - -static const struct file_operations debug_file_ops = { - .owner = THIS_MODULE, - .read = debug_output, - .write = debug_input, - .open = debug_open, - .release = debug_close, - .llseek = no_llseek, -}; - -static struct dentry *debug_debugfs_root_entry; - -/* functions */ - -/* - * debug_areas_alloc - * - Debug areas are implemented as a threedimensonal array: - * areas[areanumber][pagenumber][pageoffset] - */ - -static debug_entry_t*** -debug_areas_alloc(int pages_per_area, int nr_areas) -{ - debug_entry_t*** areas; - int i,j; - - areas = kmalloc(nr_areas * - sizeof(debug_entry_t**), - GFP_KERNEL); - if (!areas) - goto fail_malloc_areas; - for (i = 0; i < nr_areas; i++) { - areas[i] = kmalloc(pages_per_area * - sizeof(debug_entry_t*),GFP_KERNEL); - if (!areas[i]) { - goto fail_malloc_areas2; - } - for(j = 0; j < pages_per_area; j++) { - areas[i][j] = kzalloc(PAGE_SIZE, GFP_KERNEL); - if(!areas[i][j]) { - for(j--; j >=0 ; j--) { - kfree(areas[i][j]); - } - kfree(areas[i]); - goto fail_malloc_areas2; - } - } - } - return areas; - -fail_malloc_areas2: - for(i--; i >= 0; i--){ - for(j=0; j < pages_per_area;j++){ - kfree(areas[i][j]); - } - kfree(areas[i]); - } - kfree(areas); -fail_malloc_areas: - return NULL; - -} - - -/* - * debug_info_alloc - * - alloc new debug-info - */ - -static debug_info_t* -debug_info_alloc(const char *name, int pages_per_area, int nr_areas, - int buf_size, int level, int mode) -{ - debug_info_t* rc; - - /* alloc everything */ - - rc = kmalloc(sizeof(debug_info_t), GFP_KERNEL); - if(!rc) - goto fail_malloc_rc; - rc->active_entries = kcalloc(nr_areas, sizeof(int), GFP_KERNEL); - if(!rc->active_entries) - goto fail_malloc_active_entries; - rc->active_pages = kcalloc(nr_areas, sizeof(int), GFP_KERNEL); - if(!rc->active_pages) - goto fail_malloc_active_pages; - if((mode == ALL_AREAS) && (pages_per_area != 0)){ - rc->areas = debug_areas_alloc(pages_per_area, nr_areas); - if(!rc->areas) - goto fail_malloc_areas; - } else { - rc->areas = NULL; - } - - /* initialize members */ - - spin_lock_init(&rc->lock); - rc->pages_per_area = pages_per_area; - rc->nr_areas = nr_areas; - rc->active_area = 0; - rc->level = level; - rc->buf_size = buf_size; - rc->entry_size = sizeof(debug_entry_t) + buf_size; - strlcpy(rc->name, name, sizeof(rc->name)); - memset(rc->views, 0, DEBUG_MAX_VIEWS * sizeof(struct debug_view *)); - memset(rc->debugfs_entries, 0 ,DEBUG_MAX_VIEWS * - sizeof(struct dentry*)); - atomic_set(&(rc->ref_count), 0); - - return rc; - -fail_malloc_areas: - kfree(rc->active_pages); -fail_malloc_active_pages: - kfree(rc->active_entries); -fail_malloc_active_entries: - kfree(rc); -fail_malloc_rc: - return NULL; -} - -/* - * debug_areas_free - * - free all debug areas - */ - -static void -debug_areas_free(debug_info_t* db_info) -{ - int i,j; - - if(!db_info->areas) - return; - for (i = 0; i < db_info->nr_areas; i++) { - for(j = 0; j < db_info->pages_per_area; j++) { - kfree(db_info->areas[i][j]); - } - kfree(db_info->areas[i]); - } - kfree(db_info->areas); - db_info->areas = NULL; -} - -/* - * debug_info_free - * - free memory debug-info - */ - -static void -debug_info_free(debug_info_t* db_info){ - debug_areas_free(db_info); - kfree(db_info->active_entries); - kfree(db_info->active_pages); - kfree(db_info); -} - -/* - * debug_info_create - * - create new debug-info - */ - -static debug_info_t* -debug_info_create(const char *name, int pages_per_area, int nr_areas, - int buf_size, umode_t mode) -{ - debug_info_t* rc; - - rc = debug_info_alloc(name, pages_per_area, nr_areas, buf_size, - DEBUG_DEFAULT_LEVEL, ALL_AREAS); - if(!rc) - goto out; - - rc->mode = mode & ~S_IFMT; - - /* create root directory */ - rc->debugfs_root_entry = debugfs_create_dir(rc->name, - debug_debugfs_root_entry); - - /* append new element to linked list */ - if (!debug_area_first) { - /* first element in list */ - debug_area_first = rc; - rc->prev = NULL; - } else { - /* append element to end of list */ - debug_area_last->next = rc; - rc->prev = debug_area_last; - } - debug_area_last = rc; - rc->next = NULL; - - debug_info_get(rc); -out: - return rc; -} - -/* - * debug_info_copy - * - copy debug-info - */ - -static debug_info_t* -debug_info_copy(debug_info_t* in, int mode) -{ - int i,j; - debug_info_t* rc; - unsigned long flags; - - /* get a consistent copy of the debug areas */ - do { - rc = debug_info_alloc(in->name, in->pages_per_area, - in->nr_areas, in->buf_size, in->level, mode); - spin_lock_irqsave(&in->lock, flags); - if(!rc) - goto out; - /* has something changed in the meantime ? */ - if((rc->pages_per_area == in->pages_per_area) && - (rc->nr_areas == in->nr_areas)) { - break; - } - spin_unlock_irqrestore(&in->lock, flags); - debug_info_free(rc); - } while (1); - - if (mode == NO_AREAS) - goto out; - - for(i = 0; i < in->nr_areas; i++){ - for(j = 0; j < in->pages_per_area; j++) { - memcpy(rc->areas[i][j], in->areas[i][j],PAGE_SIZE); - } - } -out: - spin_unlock_irqrestore(&in->lock, flags); - return rc; -} - -/* - * debug_info_get - * - increments reference count for debug-info - */ - -static void -debug_info_get(debug_info_t * db_info) -{ - if (db_info) - atomic_inc(&db_info->ref_count); -} - -/* - * debug_info_put: - * - decreases reference count for debug-info and frees it if necessary - */ - -static void -debug_info_put(debug_info_t *db_info) -{ - int i; - - if (!db_info) - return; - if (atomic_dec_and_test(&db_info->ref_count)) { - for (i = 0; i < DEBUG_MAX_VIEWS; i++) { - if (!db_info->views[i]) - continue; - debugfs_remove(db_info->debugfs_entries[i]); - } - debugfs_remove(db_info->debugfs_root_entry); - if(db_info == debug_area_first) - debug_area_first = db_info->next; - if(db_info == debug_area_last) - debug_area_last = db_info->prev; - if(db_info->prev) db_info->prev->next = db_info->next; - if(db_info->next) db_info->next->prev = db_info->prev; - debug_info_free(db_info); - } -} - -/* - * debug_format_entry: - * - format one debug entry and return size of formated data - */ - -static int -debug_format_entry(file_private_info_t *p_info) -{ - debug_info_t *id_snap = p_info->debug_info_snap; - struct debug_view *view = p_info->view; - debug_entry_t *act_entry; - size_t len = 0; - if(p_info->act_entry == DEBUG_PROLOG_ENTRY){ - /* print prolog */ - if (view->prolog_proc) - len += view->prolog_proc(id_snap,view,p_info->temp_buf); - goto out; - } - if (!id_snap->areas) /* this is true, if we have a prolog only view */ - goto out; /* or if 'pages_per_area' is 0 */ - act_entry = (debug_entry_t *) ((char*)id_snap->areas[p_info->act_area] - [p_info->act_page] + p_info->act_entry); - - if (act_entry->id.stck == 0LL) - goto out; /* empty entry */ - if (view->header_proc) - len += view->header_proc(id_snap, view, p_info->act_area, - act_entry, p_info->temp_buf + len); - if (view->format_proc) - len += view->format_proc(id_snap, view, p_info->temp_buf + len, - DEBUG_DATA(act_entry)); -out: - return len; -} - -/* - * debug_next_entry: - * - goto next entry in p_info - */ - -static inline int -debug_next_entry(file_private_info_t *p_info) -{ - debug_info_t *id; - - id = p_info->debug_info_snap; - if(p_info->act_entry == DEBUG_PROLOG_ENTRY){ - p_info->act_entry = 0; - p_info->act_page = 0; - goto out; - } - if(!id->areas) - return 1; - p_info->act_entry += id->entry_size; - /* switch to next page, if we reached the end of the page */ - if (p_info->act_entry > (PAGE_SIZE - id->entry_size)){ - /* next page */ - p_info->act_entry = 0; - p_info->act_page += 1; - if((p_info->act_page % id->pages_per_area) == 0) { - /* next area */ - p_info->act_area++; - p_info->act_page=0; - } - if(p_info->act_area >= id->nr_areas) - return 1; - } -out: - return 0; -} - -/* - * debug_output: - * - called for user read() - * - copies formated debug entries to the user buffer - */ - -static ssize_t -debug_output(struct file *file, /* file descriptor */ - char __user *user_buf, /* user buffer */ - size_t len, /* length of buffer */ - loff_t *offset) /* offset in the file */ -{ - size_t count = 0; - size_t entry_offset; - file_private_info_t *p_info; - - p_info = ((file_private_info_t *) file->private_data); - if (*offset != p_info->offset) - return -EPIPE; - if(p_info->act_area >= p_info->debug_info_snap->nr_areas) - return 0; - entry_offset = p_info->act_entry_offset; - while(count < len){ - int formatted_line_size; - int formatted_line_residue; - int user_buf_residue; - size_t copy_size; - - formatted_line_size = debug_format_entry(p_info); - formatted_line_residue = formatted_line_size - entry_offset; - user_buf_residue = len-count; - copy_size = min(user_buf_residue, formatted_line_residue); - if(copy_size){ - if (copy_to_user(user_buf + count, p_info->temp_buf - + entry_offset, copy_size)) - return -EFAULT; - count += copy_size; - entry_offset += copy_size; - } - if(copy_size == formatted_line_residue){ - entry_offset = 0; - if(debug_next_entry(p_info)) - goto out; - } - } -out: - p_info->offset = *offset + count; - p_info->act_entry_offset = entry_offset; - *offset = p_info->offset; - return count; -} - -/* - * debug_input: - * - called for user write() - * - calls input function of view - */ - -static ssize_t -debug_input(struct file *file, const char __user *user_buf, size_t length, - loff_t *offset) -{ - int rc = 0; - file_private_info_t *p_info; - - mutex_lock(&debug_mutex); - p_info = ((file_private_info_t *) file->private_data); - if (p_info->view->input_proc) - rc = p_info->view->input_proc(p_info->debug_info_org, - p_info->view, file, user_buf, - length, offset); - else - rc = -EPERM; - mutex_unlock(&debug_mutex); - return rc; /* number of input characters */ -} - -/* - * debug_open: - * - called for user open() - * - copies formated output to private_data area of the file - * handle - */ - -static int -debug_open(struct inode *inode, struct file *file) -{ - int i, rc = 0; - file_private_info_t *p_info; - debug_info_t *debug_info, *debug_info_snapshot; - - mutex_lock(&debug_mutex); - debug_info = file->f_path.dentry->d_inode->i_private; - /* find debug view */ - for (i = 0; i < DEBUG_MAX_VIEWS; i++) { - if (!debug_info->views[i]) - continue; - else if (debug_info->debugfs_entries[i] == - file->f_path.dentry) { - goto found; /* found view ! */ - } - } - /* no entry found */ - rc = -EINVAL; - goto out; - -found: - - /* Make snapshot of current debug areas to get it consistent. */ - /* To copy all the areas is only needed, if we have a view which */ - /* formats the debug areas. */ - - if(!debug_info->views[i]->format_proc && - !debug_info->views[i]->header_proc){ - debug_info_snapshot = debug_info_copy(debug_info, NO_AREAS); - } else { - debug_info_snapshot = debug_info_copy(debug_info, ALL_AREAS); - } - - if(!debug_info_snapshot){ - rc = -ENOMEM; - goto out; - } - p_info = kmalloc(sizeof(file_private_info_t), - GFP_KERNEL); - if(!p_info){ - debug_info_free(debug_info_snapshot); - rc = -ENOMEM; - goto out; - } - p_info->offset = 0; - p_info->debug_info_snap = debug_info_snapshot; - p_info->debug_info_org = debug_info; - p_info->view = debug_info->views[i]; - p_info->act_area = 0; - p_info->act_page = 0; - p_info->act_entry = DEBUG_PROLOG_ENTRY; - p_info->act_entry_offset = 0; - file->private_data = p_info; - debug_info_get(debug_info); - nonseekable_open(inode, file); -out: - mutex_unlock(&debug_mutex); - return rc; -} - -/* - * debug_close: - * - called for user close() - * - deletes private_data area of the file handle - */ - -static int -debug_close(struct inode *inode, struct file *file) -{ - file_private_info_t *p_info; - p_info = (file_private_info_t *) file->private_data; - if(p_info->debug_info_snap) - debug_info_free(p_info->debug_info_snap); - debug_info_put(p_info->debug_info_org); - kfree(file->private_data); - return 0; /* success */ -} - -/* - * debug_register_mode: - * - Creates and initializes debug area for the caller - * The mode parameter allows to specify access rights for the s390dbf files - * - Returns handle for debug area - */ - -debug_info_t *debug_register_mode(const char *name, int pages_per_area, - int nr_areas, int buf_size, umode_t mode, - uid_t uid, gid_t gid) -{ - debug_info_t *rc = NULL; - - /* Since debugfs currently does not support uid/gid other than root, */ - /* we do not allow gid/uid != 0 until we get support for that. */ - if ((uid != 0) || (gid != 0)) - pr_warning("Root becomes the owner of all s390dbf files " - "in sysfs\n"); - BUG_ON(!initialized); - mutex_lock(&debug_mutex); - - /* create new debug_info */ - - rc = debug_info_create(name, pages_per_area, nr_areas, buf_size, mode); - if(!rc) - goto out; - debug_register_view(rc, &debug_level_view); - debug_register_view(rc, &debug_flush_view); - debug_register_view(rc, &debug_pages_view); -out: - if (!rc){ - pr_err("Registering debug feature %s failed\n", name); - } - mutex_unlock(&debug_mutex); - return rc; -} -EXPORT_SYMBOL(debug_register_mode); - -/* - * debug_register: - * - creates and initializes debug area for the caller - * - returns handle for debug area - */ - -debug_info_t *debug_register(const char *name, int pages_per_area, - int nr_areas, int buf_size) -{ - return debug_register_mode(name, pages_per_area, nr_areas, buf_size, - S_IRUSR | S_IWUSR, 0, 0); -} - -/* - * debug_unregister: - * - give back debug area - */ - -void -debug_unregister(debug_info_t * id) -{ - if (!id) - goto out; - mutex_lock(&debug_mutex); - debug_info_put(id); - mutex_unlock(&debug_mutex); - -out: - return; -} - -/* - * debug_set_size: - * - set area size (number of pages) and number of areas - */ -static int -debug_set_size(debug_info_t* id, int nr_areas, int pages_per_area) -{ - unsigned long flags; - debug_entry_t *** new_areas; - int rc=0; - - if(!id || (nr_areas <= 0) || (pages_per_area < 0)) - return -EINVAL; - if(pages_per_area > 0){ - new_areas = debug_areas_alloc(pages_per_area, nr_areas); - if(!new_areas) { - pr_info("Allocating memory for %i pages failed\n", - pages_per_area); - rc = -ENOMEM; - goto out; - } - } else { - new_areas = NULL; - } - spin_lock_irqsave(&id->lock,flags); - debug_areas_free(id); - id->areas = new_areas; - id->nr_areas = nr_areas; - id->pages_per_area = pages_per_area; - id->active_area = 0; - memset(id->active_entries,0,sizeof(int)*id->nr_areas); - memset(id->active_pages, 0, sizeof(int)*id->nr_areas); - spin_unlock_irqrestore(&id->lock,flags); - pr_info("%s: set new size (%i pages)\n" ,id->name, pages_per_area); -out: - return rc; -} - -/* - * debug_set_level: - * - set actual debug level - */ - -void -debug_set_level(debug_info_t* id, int new_level) -{ - unsigned long flags; - if(!id) - return; - spin_lock_irqsave(&id->lock,flags); - if(new_level == DEBUG_OFF_LEVEL){ - id->level = DEBUG_OFF_LEVEL; - pr_info("%s: switched off\n",id->name); - } else if ((new_level > DEBUG_MAX_LEVEL) || (new_level < 0)) { - pr_info("%s: level %i is out of range (%i - %i)\n", - id->name, new_level, 0, DEBUG_MAX_LEVEL); - } else { - id->level = new_level; - } - spin_unlock_irqrestore(&id->lock,flags); -} - - -/* - * proceed_active_entry: - * - set active entry to next in the ring buffer - */ - -static inline void -proceed_active_entry(debug_info_t * id) -{ - if ((id->active_entries[id->active_area] += id->entry_size) - > (PAGE_SIZE - id->entry_size)){ - id->active_entries[id->active_area] = 0; - id->active_pages[id->active_area] = - (id->active_pages[id->active_area] + 1) % - id->pages_per_area; - } -} - -/* - * proceed_active_area: - * - set active area to next in the ring buffer - */ - -static inline void -proceed_active_area(debug_info_t * id) -{ - id->active_area++; - id->active_area = id->active_area % id->nr_areas; -} - -/* - * get_active_entry: - */ - -static inline debug_entry_t* -get_active_entry(debug_info_t * id) -{ - return (debug_entry_t *) (((char *) id->areas[id->active_area] - [id->active_pages[id->active_area]]) + - id->active_entries[id->active_area]); -} - -/* - * debug_finish_entry: - * - set timestamp, caller address, cpu number etc. - */ - -static inline void -debug_finish_entry(debug_info_t * id, debug_entry_t* active, int level, - int exception) -{ - active->id.stck = get_clock(); - active->id.fields.cpuid = smp_processor_id(); - active->caller = __builtin_return_address(0); - active->id.fields.exception = exception; - active->id.fields.level = level; - proceed_active_entry(id); - if(exception) - proceed_active_area(id); -} - -static int debug_stoppable=1; -static int debug_active=1; - -#define CTL_S390DBF_STOPPABLE 5678 -#define CTL_S390DBF_ACTIVE 5679 - -/* - * proc handler for the running debug_active sysctl - * always allow read, allow write only if debug_stoppable is set or - * if debug_active is already off - */ -static int -s390dbf_procactive(ctl_table *table, int write, - void __user *buffer, size_t *lenp, loff_t *ppos) -{ - if (!write || debug_stoppable || !debug_active) - return proc_dointvec(table, write, buffer, lenp, ppos); - else - return 0; -} - - -static struct ctl_table s390dbf_table[] = { - { - .procname = "debug_stoppable", - .data = &debug_stoppable, - .maxlen = sizeof(int), - .mode = S_IRUGO | S_IWUSR, - .proc_handler = proc_dointvec, - }, - { - .procname = "debug_active", - .data = &debug_active, - .maxlen = sizeof(int), - .mode = S_IRUGO | S_IWUSR, - .proc_handler = s390dbf_procactive, - }, - { } -}; - -static struct ctl_table s390dbf_dir_table[] = { - { - .procname = "s390dbf", - .maxlen = 0, - .mode = S_IRUGO | S_IXUGO, - .child = s390dbf_table, - }, - { } -}; - -static struct ctl_table_header *s390dbf_sysctl_header; - -void -debug_stop_all(void) -{ - if (debug_stoppable) - debug_active = 0; -} - - -void debug_set_critical(void) -{ - debug_critical = 1; -} - -/* - * debug_event_common: - * - write debug entry with given size - */ - -debug_entry_t* -debug_event_common(debug_info_t * id, int level, const void *buf, int len) -{ - unsigned long flags; - debug_entry_t *active; - - if (!debug_active || !id->areas) - return NULL; - if (debug_critical) { - if (!spin_trylock_irqsave(&id->lock, flags)) - return NULL; - } else - spin_lock_irqsave(&id->lock, flags); - active = get_active_entry(id); - memset(DEBUG_DATA(active), 0, id->buf_size); - memcpy(DEBUG_DATA(active), buf, min(len, id->buf_size)); - debug_finish_entry(id, active, level, 0); - spin_unlock_irqrestore(&id->lock, flags); - - return active; -} - -/* - * debug_exception_common: - * - write debug entry with given size and switch to next debug area - */ - -debug_entry_t -*debug_exception_common(debug_info_t * id, int level, const void *buf, int len) -{ - unsigned long flags; - debug_entry_t *active; - - if (!debug_active || !id->areas) - return NULL; - if (debug_critical) { - if (!spin_trylock_irqsave(&id->lock, flags)) - return NULL; - } else - spin_lock_irqsave(&id->lock, flags); - active = get_active_entry(id); - memset(DEBUG_DATA(active), 0, id->buf_size); - memcpy(DEBUG_DATA(active), buf, min(len, id->buf_size)); - debug_finish_entry(id, active, level, 1); - spin_unlock_irqrestore(&id->lock, flags); - - return active; -} - -/* - * counts arguments in format string for sprintf view - */ - -static inline int -debug_count_numargs(char *string) -{ - int numargs=0; - - while(*string) { - if(*string++=='%') - numargs++; - } - return(numargs); -} - -/* - * debug_sprintf_event: - */ - -debug_entry_t* -debug_sprintf_event(debug_info_t* id, int level,char *string,...) -{ - va_list ap; - int numargs,idx; - unsigned long flags; - debug_sprintf_entry_t *curr_event; - debug_entry_t *active; - - if((!id) || (level > id->level)) - return NULL; - if (!debug_active || !id->areas) - return NULL; - numargs=debug_count_numargs(string); - - if (debug_critical) { - if (!spin_trylock_irqsave(&id->lock, flags)) - return NULL; - } else - spin_lock_irqsave(&id->lock, flags); - active = get_active_entry(id); - curr_event=(debug_sprintf_entry_t *) DEBUG_DATA(active); - va_start(ap,string); - curr_event->string=string; - for(idx=0;idx<min(numargs,(int)(id->buf_size / sizeof(long))-1);idx++) - curr_event->args[idx]=va_arg(ap,long); - va_end(ap); - debug_finish_entry(id, active, level, 0); - spin_unlock_irqrestore(&id->lock, flags); - - return active; -} - -/* - * debug_sprintf_exception: - */ - -debug_entry_t* -debug_sprintf_exception(debug_info_t* id, int level,char *string,...) -{ - va_list ap; - int numargs,idx; - unsigned long flags; - debug_sprintf_entry_t *curr_event; - debug_entry_t *active; - - if((!id) || (level > id->level)) - return NULL; - if (!debug_active || !id->areas) - return NULL; - - numargs=debug_count_numargs(string); - - if (debug_critical) { - if (!spin_trylock_irqsave(&id->lock, flags)) - return NULL; - } else - spin_lock_irqsave(&id->lock, flags); - active = get_active_entry(id); - curr_event=(debug_sprintf_entry_t *)DEBUG_DATA(active); - va_start(ap,string); - curr_event->string=string; - for(idx=0;idx<min(numargs,(int)(id->buf_size / sizeof(long))-1);idx++) - curr_event->args[idx]=va_arg(ap,long); - va_end(ap); - debug_finish_entry(id, active, level, 1); - spin_unlock_irqrestore(&id->lock, flags); - - return active; -} - -/* - * debug_init: - * - is called exactly once to initialize the debug feature - */ - -static int -__init debug_init(void) -{ - int rc = 0; - - s390dbf_sysctl_header = register_sysctl_table(s390dbf_dir_table); - mutex_lock(&debug_mutex); - debug_debugfs_root_entry = debugfs_create_dir(DEBUG_DIR_ROOT,NULL); - initialized = 1; - mutex_unlock(&debug_mutex); - - return rc; -} - -/* - * debug_register_view: - */ - -int -debug_register_view(debug_info_t * id, struct debug_view *view) -{ - int rc = 0; - int i; - unsigned long flags; - umode_t mode; - struct dentry *pde; - - if (!id) - goto out; - mode = (id->mode | S_IFREG) & ~S_IXUGO; - if (!(view->prolog_proc || view->format_proc || view->header_proc)) - mode &= ~(S_IRUSR | S_IRGRP | S_IROTH); - if (!view->input_proc) - mode &= ~(S_IWUSR | S_IWGRP | S_IWOTH); - pde = debugfs_create_file(view->name, mode, id->debugfs_root_entry, - id , &debug_file_ops); - if (!pde){ - pr_err("Registering view %s/%s failed due to out of " - "memory\n", id->name,view->name); - rc = -1; - goto out; - } - spin_lock_irqsave(&id->lock, flags); - for (i = 0; i < DEBUG_MAX_VIEWS; i++) { - if (!id->views[i]) - break; - } - if (i == DEBUG_MAX_VIEWS) { - pr_err("Registering view %s/%s would exceed the maximum " - "number of views %i\n", id->name, view->name, i); - debugfs_remove(pde); - rc = -1; - } else { - id->views[i] = view; - id->debugfs_entries[i] = pde; - } - spin_unlock_irqrestore(&id->lock, flags); -out: - return rc; -} - -/* - * debug_unregister_view: - */ - -int -debug_unregister_view(debug_info_t * id, struct debug_view *view) -{ - int rc = 0; - int i; - unsigned long flags; - - if (!id) - goto out; - spin_lock_irqsave(&id->lock, flags); - for (i = 0; i < DEBUG_MAX_VIEWS; i++) { - if (id->views[i] == view) - break; - } - if (i == DEBUG_MAX_VIEWS) - rc = -1; - else { - debugfs_remove(id->debugfs_entries[i]); - id->views[i] = NULL; - } - spin_unlock_irqrestore(&id->lock, flags); -out: - return rc; -} - -static inline char * -debug_get_user_string(const char __user *user_buf, size_t user_len) -{ - char* buffer; - - buffer = kmalloc(user_len + 1, GFP_KERNEL); - if (!buffer) - return ERR_PTR(-ENOMEM); - if (copy_from_user(buffer, user_buf, user_len) != 0) { - kfree(buffer); - return ERR_PTR(-EFAULT); - } - /* got the string, now strip linefeed. */ - if (buffer[user_len - 1] == '\n') - buffer[user_len - 1] = 0; - else - buffer[user_len] = 0; - return buffer; -} - -static inline int -debug_get_uint(char *buf) -{ - int rc; - - buf = skip_spaces(buf); - rc = simple_strtoul(buf, &buf, 10); - if(*buf){ - rc = -EINVAL; - } - return rc; -} - -/* - * functions for debug-views - *********************************** -*/ - -/* - * prints out actual debug level - */ - -static int -debug_prolog_pages_fn(debug_info_t * id, - struct debug_view *view, char *out_buf) -{ - return sprintf(out_buf, "%i\n", id->pages_per_area); -} - -/* - * reads new size (number of pages per debug area) - */ - -static int -debug_input_pages_fn(debug_info_t * id, struct debug_view *view, - struct file *file, const char __user *user_buf, - size_t user_len, loff_t * offset) -{ - char *str; - int rc,new_pages; - - if (user_len > 0x10000) - user_len = 0x10000; - if (*offset != 0){ - rc = -EPIPE; - goto out; - } - str = debug_get_user_string(user_buf,user_len); - if(IS_ERR(str)){ - rc = PTR_ERR(str); - goto out; - } - new_pages = debug_get_uint(str); - if(new_pages < 0){ - rc = -EINVAL; - goto free_str; - } - rc = debug_set_size(id,id->nr_areas, new_pages); - if(rc != 0){ - rc = -EINVAL; - goto free_str; - } - rc = user_len; -free_str: - kfree(str); -out: - *offset += user_len; - return rc; /* number of input characters */ -} - -/* - * prints out actual debug level - */ - -static int -debug_prolog_level_fn(debug_info_t * id, struct debug_view *view, char *out_buf) -{ - int rc = 0; - - if(id->level == DEBUG_OFF_LEVEL) { - rc = sprintf(out_buf,"-\n"); - } - else { - rc = sprintf(out_buf, "%i\n", id->level); - } - return rc; -} - -/* - * reads new debug level - */ - -static int -debug_input_level_fn(debug_info_t * id, struct debug_view *view, - struct file *file, const char __user *user_buf, - size_t user_len, loff_t * offset) -{ - char *str; - int rc,new_level; - - if (user_len > 0x10000) - user_len = 0x10000; - if (*offset != 0){ - rc = -EPIPE; - goto out; - } - str = debug_get_user_string(user_buf,user_len); - if(IS_ERR(str)){ - rc = PTR_ERR(str); - goto out; - } - if(str[0] == '-'){ - debug_set_level(id, DEBUG_OFF_LEVEL); - rc = user_len; - goto free_str; - } else { - new_level = debug_get_uint(str); - } - if(new_level < 0) { - pr_warning("%s is not a valid level for a debug " - "feature\n", str); - rc = -EINVAL; - } else { - debug_set_level(id, new_level); - rc = user_len; - } -free_str: - kfree(str); -out: - *offset += user_len; - return rc; /* number of input characters */ -} - - -/* - * flushes debug areas - */ - -static void debug_flush(debug_info_t* id, int area) -{ - unsigned long flags; - int i,j; - - if(!id || !id->areas) - return; - spin_lock_irqsave(&id->lock,flags); - if(area == DEBUG_FLUSH_ALL){ - id->active_area = 0; - memset(id->active_entries, 0, id->nr_areas * sizeof(int)); - for (i = 0; i < id->nr_areas; i++) { - id->active_pages[i] = 0; - for(j = 0; j < id->pages_per_area; j++) { - memset(id->areas[i][j], 0, PAGE_SIZE); - } - } - } else if(area >= 0 && area < id->nr_areas) { - id->active_entries[area] = 0; - id->active_pages[area] = 0; - for(i = 0; i < id->pages_per_area; i++) { - memset(id->areas[area][i],0,PAGE_SIZE); - } - } - spin_unlock_irqrestore(&id->lock,flags); -} - -/* - * view function: flushes debug areas - */ - -static int -debug_input_flush_fn(debug_info_t * id, struct debug_view *view, - struct file *file, const char __user *user_buf, - size_t user_len, loff_t * offset) -{ - char input_buf[1]; - int rc = user_len; - - if (user_len > 0x10000) - user_len = 0x10000; - if (*offset != 0){ - rc = -EPIPE; - goto out; - } - if (copy_from_user(input_buf, user_buf, 1)){ - rc = -EFAULT; - goto out; - } - if(input_buf[0] == '-') { - debug_flush(id, DEBUG_FLUSH_ALL); - goto out; - } - if (isdigit(input_buf[0])) { - int area = ((int) input_buf[0] - (int) '0'); - debug_flush(id, area); - goto out; - } - - pr_info("Flushing debug data failed because %c is not a valid " - "area\n", input_buf[0]); - -out: - *offset += user_len; - return rc; /* number of input characters */ -} - -/* - * prints debug header in raw format - */ - -static int -debug_raw_header_fn(debug_info_t * id, struct debug_view *view, - int area, debug_entry_t * entry, char *out_buf) -{ - int rc; - - rc = sizeof(debug_entry_t); - memcpy(out_buf,entry,sizeof(debug_entry_t)); - return rc; -} - -/* - * prints debug data in raw format - */ - -static int -debug_raw_format_fn(debug_info_t * id, struct debug_view *view, - char *out_buf, const char *in_buf) -{ - int rc; - - rc = id->buf_size; - memcpy(out_buf, in_buf, id->buf_size); - return rc; -} - -/* - * prints debug data in hex/ascii format - */ - -static int -debug_hex_ascii_format_fn(debug_info_t * id, struct debug_view *view, - char *out_buf, const char *in_buf) -{ - int i, rc = 0; - - for (i = 0; i < id->buf_size; i++) { - rc += sprintf(out_buf + rc, "%02x ", - ((unsigned char *) in_buf)[i]); - } - rc += sprintf(out_buf + rc, "| "); - for (i = 0; i < id->buf_size; i++) { - unsigned char c = in_buf[i]; - if (isascii(c) && isprint(c)) - rc += sprintf(out_buf + rc, "%c", c); - else - rc += sprintf(out_buf + rc, "."); - } - rc += sprintf(out_buf + rc, "\n"); - return rc; -} - -/* - * prints header for debug entry - */ - -int -debug_dflt_header_fn(debug_info_t * id, struct debug_view *view, - int area, debug_entry_t * entry, char *out_buf) -{ - struct timespec time_spec; - char *except_str; - unsigned long caller; - int rc = 0; - unsigned int level; - - level = entry->id.fields.level; - stck_to_timespec(entry->id.stck, &time_spec); - - if (entry->id.fields.exception) - except_str = "*"; - else - except_str = "-"; - caller = ((unsigned long) entry->caller) & PSW_ADDR_INSN; - rc += sprintf(out_buf, "%02i %011lu:%06lu %1u %1s %02i %p ", - area, time_spec.tv_sec, time_spec.tv_nsec / 1000, level, - except_str, entry->id.fields.cpuid, (void *) caller); - return rc; -} - -/* - * prints debug data sprintf-formated: - * debug_sprinf_event/exception calls must be used together with this view - */ - -#define DEBUG_SPRINTF_MAX_ARGS 10 - -static int -debug_sprintf_format_fn(debug_info_t * id, struct debug_view *view, - char *out_buf, debug_sprintf_entry_t *curr_event) -{ - int num_longs, num_used_args = 0,i, rc = 0; - int index[DEBUG_SPRINTF_MAX_ARGS]; - - /* count of longs fit into one entry */ - num_longs = id->buf_size / sizeof(long); - - if(num_longs < 1) - goto out; /* bufsize of entry too small */ - if(num_longs == 1) { - /* no args, we use only the string */ - strcpy(out_buf, curr_event->string); - rc = strlen(curr_event->string); - goto out; - } - - /* number of arguments used for sprintf (without the format string) */ - num_used_args = min(DEBUG_SPRINTF_MAX_ARGS, (num_longs - 1)); - - memset(index,0, DEBUG_SPRINTF_MAX_ARGS * sizeof(int)); - - for(i = 0; i < num_used_args; i++) - index[i] = i; - - rc = sprintf(out_buf, curr_event->string, curr_event->args[index[0]], - curr_event->args[index[1]], curr_event->args[index[2]], - curr_event->args[index[3]], curr_event->args[index[4]], - curr_event->args[index[5]], curr_event->args[index[6]], - curr_event->args[index[7]], curr_event->args[index[8]], - curr_event->args[index[9]]); - -out: - - return rc; -} - -/* - * clean up module - */ -static void __exit debug_exit(void) -{ - debugfs_remove(debug_debugfs_root_entry); - unregister_sysctl_table(s390dbf_sysctl_header); - return; -} - -/* - * module definitions - */ -postcore_initcall(debug_init); -module_exit(debug_exit); -MODULE_LICENSE("GPL"); - -EXPORT_SYMBOL(debug_register); -EXPORT_SYMBOL(debug_unregister); -EXPORT_SYMBOL(debug_set_level); -EXPORT_SYMBOL(debug_stop_all); -EXPORT_SYMBOL(debug_register_view); -EXPORT_SYMBOL(debug_unregister_view); -EXPORT_SYMBOL(debug_event_common); -EXPORT_SYMBOL(debug_exception_common); -EXPORT_SYMBOL(debug_hex_ascii_view); -EXPORT_SYMBOL(debug_raw_view); -EXPORT_SYMBOL(debug_dflt_header_fn); -EXPORT_SYMBOL(debug_sprintf_view); -EXPORT_SYMBOL(debug_sprintf_exception); -EXPORT_SYMBOL(debug_sprintf_event); diff --git a/ANDROID_3.4.5/arch/s390/kernel/diag.c b/ANDROID_3.4.5/arch/s390/kernel/diag.c deleted file mode 100644 index 8237fc07..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/diag.c +++ /dev/null @@ -1,81 +0,0 @@ -/* - * Implementation of s390 diagnose codes - * - * Copyright IBM Corp. 2007 - * Author(s): Michael Holzheu <holzheu@de.ibm.com> - */ - -#include <linux/module.h> -#include <asm/diag.h> - -/* - * Diagnose 14: Input spool file manipulation - */ -int diag14(unsigned long rx, unsigned long ry1, unsigned long subcode) -{ - register unsigned long _ry1 asm("2") = ry1; - register unsigned long _ry2 asm("3") = subcode; - int rc = 0; - - asm volatile( -#ifdef CONFIG_64BIT - " sam31\n" - " diag %2,2,0x14\n" - " sam64\n" -#else - " diag %2,2,0x14\n" -#endif - " ipm %0\n" - " srl %0,28\n" - : "=d" (rc), "+d" (_ry2) - : "d" (rx), "d" (_ry1) - : "cc"); - - return rc; -} -EXPORT_SYMBOL(diag14); - -/* - * Diagnose 210: Get information about a virtual device - */ -int diag210(struct diag210 *addr) -{ - /* - * diag 210 needs its data below the 2GB border, so we - * use a static data area to be sure - */ - static struct diag210 diag210_tmp; - static DEFINE_SPINLOCK(diag210_lock); - unsigned long flags; - int ccode; - - spin_lock_irqsave(&diag210_lock, flags); - diag210_tmp = *addr; - -#ifdef CONFIG_64BIT - asm volatile( - " lhi %0,-1\n" - " sam31\n" - " diag %1,0,0x210\n" - "0: ipm %0\n" - " srl %0,28\n" - "1: sam64\n" - EX_TABLE(0b, 1b) - : "=&d" (ccode) : "a" (&diag210_tmp) : "cc", "memory"); -#else - asm volatile( - " lhi %0,-1\n" - " diag %1,0,0x210\n" - "0: ipm %0\n" - " srl %0,28\n" - "1:\n" - EX_TABLE(0b, 1b) - : "=&d" (ccode) : "a" (&diag210_tmp) : "cc", "memory"); -#endif - - *addr = diag210_tmp; - spin_unlock_irqrestore(&diag210_lock, flags); - - return ccode; -} -EXPORT_SYMBOL(diag210); diff --git a/ANDROID_3.4.5/arch/s390/kernel/dis.c b/ANDROID_3.4.5/arch/s390/kernel/dis.c deleted file mode 100644 index 3221c6fc..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/dis.c +++ /dev/null @@ -1,1604 +0,0 @@ -/* - * arch/s390/kernel/dis.c - * - * Disassemble s390 instructions. - * - * Copyright IBM Corp. 2007 - * Author(s): Martin Schwidefsky (schwidefsky@de.ibm.com), - */ - -#include <linux/sched.h> -#include <linux/kernel.h> -#include <linux/string.h> -#include <linux/errno.h> -#include <linux/ptrace.h> -#include <linux/timer.h> -#include <linux/mm.h> -#include <linux/smp.h> -#include <linux/init.h> -#include <linux/interrupt.h> -#include <linux/delay.h> -#include <linux/module.h> -#include <linux/kallsyms.h> -#include <linux/reboot.h> -#include <linux/kprobes.h> -#include <linux/kdebug.h> - -#include <asm/uaccess.h> -#include <asm/io.h> -#include <linux/atomic.h> -#include <asm/mathemu.h> -#include <asm/cpcmd.h> -#include <asm/lowcore.h> -#include <asm/debug.h> -#include <asm/irq.h> - -#ifndef CONFIG_64BIT -#define ONELONG "%08lx: " -#else /* CONFIG_64BIT */ -#define ONELONG "%016lx: " -#endif /* CONFIG_64BIT */ - -#define OPERAND_GPR 0x1 /* Operand printed as %rx */ -#define OPERAND_FPR 0x2 /* Operand printed as %fx */ -#define OPERAND_AR 0x4 /* Operand printed as %ax */ -#define OPERAND_CR 0x8 /* Operand printed as %cx */ -#define OPERAND_DISP 0x10 /* Operand printed as displacement */ -#define OPERAND_BASE 0x20 /* Operand printed as base register */ -#define OPERAND_INDEX 0x40 /* Operand printed as index register */ -#define OPERAND_PCREL 0x80 /* Operand printed as pc-relative symbol */ -#define OPERAND_SIGNED 0x100 /* Operand printed as signed value */ -#define OPERAND_LENGTH 0x200 /* Operand printed as length (+1) */ - -enum { - UNUSED, /* Indicates the end of the operand list */ - R_8, /* GPR starting at position 8 */ - R_12, /* GPR starting at position 12 */ - R_16, /* GPR starting at position 16 */ - R_20, /* GPR starting at position 20 */ - R_24, /* GPR starting at position 24 */ - R_28, /* GPR starting at position 28 */ - R_32, /* GPR starting at position 32 */ - F_8, /* FPR starting at position 8 */ - F_12, /* FPR starting at position 12 */ - F_16, /* FPR starting at position 16 */ - F_20, /* FPR starting at position 16 */ - F_24, /* FPR starting at position 24 */ - F_28, /* FPR starting at position 28 */ - F_32, /* FPR starting at position 32 */ - A_8, /* Access reg. starting at position 8 */ - A_12, /* Access reg. starting at position 12 */ - A_24, /* Access reg. starting at position 24 */ - A_28, /* Access reg. starting at position 28 */ - C_8, /* Control reg. starting at position 8 */ - C_12, /* Control reg. starting at position 12 */ - B_16, /* Base register starting at position 16 */ - B_32, /* Base register starting at position 32 */ - X_12, /* Index register starting at position 12 */ - D_20, /* Displacement starting at position 20 */ - D_36, /* Displacement starting at position 36 */ - D20_20, /* 20 bit displacement starting at 20 */ - L4_8, /* 4 bit length starting at position 8 */ - L4_12, /* 4 bit length starting at position 12 */ - L8_8, /* 8 bit length starting at position 8 */ - U4_8, /* 4 bit unsigned value starting at 8 */ - U4_12, /* 4 bit unsigned value starting at 12 */ - U4_16, /* 4 bit unsigned value starting at 16 */ - U4_20, /* 4 bit unsigned value starting at 20 */ - U4_32, /* 4 bit unsigned value starting at 32 */ - U8_8, /* 8 bit unsigned value starting at 8 */ - U8_16, /* 8 bit unsigned value starting at 16 */ - U8_24, /* 8 bit unsigned value starting at 24 */ - U8_32, /* 8 bit unsigned value starting at 32 */ - I8_8, /* 8 bit signed value starting at 8 */ - I8_32, /* 8 bit signed value starting at 32 */ - I16_16, /* 16 bit signed value starting at 16 */ - I16_32, /* 32 bit signed value starting at 16 */ - U16_16, /* 16 bit unsigned value starting at 16 */ - U16_32, /* 32 bit unsigned value starting at 16 */ - J16_16, /* PC relative jump offset at 16 */ - J32_16, /* PC relative long offset at 16 */ - I32_16, /* 32 bit signed value starting at 16 */ - U32_16, /* 32 bit unsigned value starting at 16 */ - M_16, /* 4 bit optional mask starting at 16 */ - RO_28, /* optional GPR starting at position 28 */ -}; - -/* - * Enumeration of the different instruction formats. - * For details consult the principles of operation. - */ -enum { - INSTR_INVALID, - INSTR_E, - INSTR_RIE_R0IU, INSTR_RIE_R0UU, INSTR_RIE_RRP, INSTR_RIE_RRPU, - INSTR_RIE_RRUUU, INSTR_RIE_RUPI, INSTR_RIE_RUPU, INSTR_RIE_RRI0, - INSTR_RIL_RI, INSTR_RIL_RP, INSTR_RIL_RU, INSTR_RIL_UP, - INSTR_RIS_R0RDU, INSTR_RIS_R0UU, INSTR_RIS_RURDI, INSTR_RIS_RURDU, - INSTR_RI_RI, INSTR_RI_RP, INSTR_RI_RU, INSTR_RI_UP, - INSTR_RRE_00, INSTR_RRE_0R, INSTR_RRE_AA, INSTR_RRE_AR, INSTR_RRE_F0, - INSTR_RRE_FF, INSTR_RRE_FR, INSTR_RRE_R0, INSTR_RRE_RA, INSTR_RRE_RF, - INSTR_RRE_RR, INSTR_RRE_RR_OPT, - INSTR_RRF_0UFF, INSTR_RRF_F0FF, INSTR_RRF_F0FF2, INSTR_RRF_F0FR, - INSTR_RRF_FFRU, INSTR_RRF_FUFF, INSTR_RRF_M0RR, INSTR_RRF_R0RR, - INSTR_RRF_R0RR2, INSTR_RRF_RURR, INSTR_RRF_U0FF, INSTR_RRF_U0RF, - INSTR_RRF_U0RR, INSTR_RRF_UUFF, INSTR_RRR_F0FF, INSTR_RRS_RRRDU, - INSTR_RR_FF, INSTR_RR_R0, INSTR_RR_RR, INSTR_RR_U0, INSTR_RR_UR, - INSTR_RSE_CCRD, INSTR_RSE_RRRD, INSTR_RSE_RURD, - INSTR_RSI_RRP, - INSTR_RSL_R0RD, - INSTR_RSY_AARD, INSTR_RSY_CCRD, INSTR_RSY_RRRD, INSTR_RSY_RURD, - INSTR_RSY_RDRM, - INSTR_RS_AARD, INSTR_RS_CCRD, INSTR_RS_R0RD, INSTR_RS_RRRD, - INSTR_RS_RURD, - INSTR_RXE_FRRD, INSTR_RXE_RRRD, - INSTR_RXF_FRRDF, - INSTR_RXY_FRRD, INSTR_RXY_RRRD, INSTR_RXY_URRD, - INSTR_RX_FRRD, INSTR_RX_RRRD, INSTR_RX_URRD, - INSTR_SIL_RDI, INSTR_SIL_RDU, - INSTR_SIY_IRD, INSTR_SIY_URD, - INSTR_SI_URD, - INSTR_SSE_RDRD, - INSTR_SSF_RRDRD, INSTR_SSF_RRDRD2, - INSTR_SS_L0RDRD, INSTR_SS_LIRDRD, INSTR_SS_LLRDRD, INSTR_SS_RRRDRD, - INSTR_SS_RRRDRD2, INSTR_SS_RRRDRD3, - INSTR_S_00, INSTR_S_RD, -}; - -struct operand { - int bits; /* The number of bits in the operand. */ - int shift; /* The number of bits to shift. */ - int flags; /* One bit syntax flags. */ -}; - -struct insn { - const char name[5]; - unsigned char opfrag; - unsigned char format; -}; - -static const struct operand operands[] = -{ - [UNUSED] = { 0, 0, 0 }, - [R_8] = { 4, 8, OPERAND_GPR }, - [R_12] = { 4, 12, OPERAND_GPR }, - [R_16] = { 4, 16, OPERAND_GPR }, - [R_20] = { 4, 20, OPERAND_GPR }, - [R_24] = { 4, 24, OPERAND_GPR }, - [R_28] = { 4, 28, OPERAND_GPR }, - [R_32] = { 4, 32, OPERAND_GPR }, - [F_8] = { 4, 8, OPERAND_FPR }, - [F_12] = { 4, 12, OPERAND_FPR }, - [F_16] = { 4, 16, OPERAND_FPR }, - [F_20] = { 4, 16, OPERAND_FPR }, - [F_24] = { 4, 24, OPERAND_FPR }, - [F_28] = { 4, 28, OPERAND_FPR }, - [F_32] = { 4, 32, OPERAND_FPR }, - [A_8] = { 4, 8, OPERAND_AR }, - [A_12] = { 4, 12, OPERAND_AR }, - [A_24] = { 4, 24, OPERAND_AR }, - [A_28] = { 4, 28, OPERAND_AR }, - [C_8] = { 4, 8, OPERAND_CR }, - [C_12] = { 4, 12, OPERAND_CR }, - [B_16] = { 4, 16, OPERAND_BASE | OPERAND_GPR }, - [B_32] = { 4, 32, OPERAND_BASE | OPERAND_GPR }, - [X_12] = { 4, 12, OPERAND_INDEX | OPERAND_GPR }, - [D_20] = { 12, 20, OPERAND_DISP }, - [D_36] = { 12, 36, OPERAND_DISP }, - [D20_20] = { 20, 20, OPERAND_DISP | OPERAND_SIGNED }, - [L4_8] = { 4, 8, OPERAND_LENGTH }, - [L4_12] = { 4, 12, OPERAND_LENGTH }, - [L8_8] = { 8, 8, OPERAND_LENGTH }, - [U4_8] = { 4, 8, 0 }, - [U4_12] = { 4, 12, 0 }, - [U4_16] = { 4, 16, 0 }, - [U4_20] = { 4, 20, 0 }, - [U4_32] = { 4, 32, 0 }, - [U8_8] = { 8, 8, 0 }, - [U8_16] = { 8, 16, 0 }, - [U8_24] = { 8, 24, 0 }, - [U8_32] = { 8, 32, 0 }, - [I16_16] = { 16, 16, OPERAND_SIGNED }, - [U16_16] = { 16, 16, 0 }, - [U16_32] = { 16, 32, 0 }, - [J16_16] = { 16, 16, OPERAND_PCREL }, - [I16_32] = { 16, 32, OPERAND_SIGNED }, - [J32_16] = { 32, 16, OPERAND_PCREL }, - [I32_16] = { 32, 16, OPERAND_SIGNED }, - [U32_16] = { 32, 16, 0 }, - [M_16] = { 4, 16, 0 }, - [RO_28] = { 4, 28, OPERAND_GPR } -}; - -static const unsigned char formats[][7] = { - [INSTR_E] = { 0xff, 0,0,0,0,0,0 }, - [INSTR_RIE_R0UU] = { 0xff, R_8,U16_16,U4_32,0,0,0 }, - [INSTR_RIE_RRPU] = { 0xff, R_8,R_12,U4_32,J16_16,0,0 }, - [INSTR_RIE_RRP] = { 0xff, R_8,R_12,J16_16,0,0,0 }, - [INSTR_RIE_RRUUU] = { 0xff, R_8,R_12,U8_16,U8_24,U8_32,0 }, - [INSTR_RIE_RUPI] = { 0xff, R_8,I8_32,U4_12,J16_16,0,0 }, - [INSTR_RIE_RRI0] = { 0xff, R_8,R_12,I16_16,0,0,0 }, - [INSTR_RIL_RI] = { 0x0f, R_8,I32_16,0,0,0,0 }, - [INSTR_RIL_RP] = { 0x0f, R_8,J32_16,0,0,0,0 }, - [INSTR_RIL_RU] = { 0x0f, R_8,U32_16,0,0,0,0 }, - [INSTR_RIL_UP] = { 0x0f, U4_8,J32_16,0,0,0,0 }, - [INSTR_RIS_R0RDU] = { 0xff, R_8,U8_32,D_20,B_16,0,0 }, - [INSTR_RIS_RURDI] = { 0xff, R_8,I8_32,U4_12,D_20,B_16,0 }, - [INSTR_RIS_RURDU] = { 0xff, R_8,U8_32,U4_12,D_20,B_16,0 }, - [INSTR_RI_RI] = { 0x0f, R_8,I16_16,0,0,0,0 }, - [INSTR_RI_RP] = { 0x0f, R_8,J16_16,0,0,0,0 }, - [INSTR_RI_RU] = { 0x0f, R_8,U16_16,0,0,0,0 }, - [INSTR_RI_UP] = { 0x0f, U4_8,J16_16,0,0,0,0 }, - [INSTR_RRE_00] = { 0xff, 0,0,0,0,0,0 }, - [INSTR_RRE_0R] = { 0xff, R_28,0,0,0,0,0 }, - [INSTR_RRE_AA] = { 0xff, A_24,A_28,0,0,0,0 }, - [INSTR_RRE_AR] = { 0xff, A_24,R_28,0,0,0,0 }, - [INSTR_RRE_F0] = { 0xff, F_24,0,0,0,0,0 }, - [INSTR_RRE_FF] = { 0xff, F_24,F_28,0,0,0,0 }, - [INSTR_RRE_FR] = { 0xff, F_24,R_28,0,0,0,0 }, - [INSTR_RRE_R0] = { 0xff, R_24,0,0,0,0,0 }, - [INSTR_RRE_RA] = { 0xff, R_24,A_28,0,0,0,0 }, - [INSTR_RRE_RF] = { 0xff, R_24,F_28,0,0,0,0 }, - [INSTR_RRE_RR] = { 0xff, R_24,R_28,0,0,0,0 }, - [INSTR_RRE_RR_OPT]= { 0xff, R_24,RO_28,0,0,0,0 }, - [INSTR_RRF_0UFF] = { 0xff, F_24,F_28,U4_20,0,0,0 }, - [INSTR_RRF_F0FF2] = { 0xff, F_24,F_16,F_28,0,0,0 }, - [INSTR_RRF_F0FF] = { 0xff, F_16,F_24,F_28,0,0,0 }, - [INSTR_RRF_F0FR] = { 0xff, F_24,F_16,R_28,0,0,0 }, - [INSTR_RRF_FFRU] = { 0xff, F_24,F_16,R_28,U4_20,0,0 }, - [INSTR_RRF_FUFF] = { 0xff, F_24,F_16,F_28,U4_20,0,0 }, - [INSTR_RRF_M0RR] = { 0xff, R_24,R_28,M_16,0,0,0 }, - [INSTR_RRF_R0RR] = { 0xff, R_24,R_16,R_28,0,0,0 }, - [INSTR_RRF_R0RR2] = { 0xff, R_24,R_28,R_16,0,0,0 }, - [INSTR_RRF_RURR] = { 0xff, R_24,R_28,R_16,U4_20,0,0 }, - [INSTR_RRF_U0FF] = { 0xff, F_24,U4_16,F_28,0,0,0 }, - [INSTR_RRF_U0RF] = { 0xff, R_24,U4_16,F_28,0,0,0 }, - [INSTR_RRF_U0RR] = { 0xff, R_24,R_28,U4_16,0,0,0 }, - [INSTR_RRF_UUFF] = { 0xff, F_24,U4_16,F_28,U4_20,0,0 }, - [INSTR_RRR_F0FF] = { 0xff, F_24,F_28,F_16,0,0,0 }, - [INSTR_RRS_RRRDU] = { 0xff, R_8,R_12,U4_32,D_20,B_16,0 }, - [INSTR_RR_FF] = { 0xff, F_8,F_12,0,0,0,0 }, - [INSTR_RR_R0] = { 0xff, R_8, 0,0,0,0,0 }, - [INSTR_RR_RR] = { 0xff, R_8,R_12,0,0,0,0 }, - [INSTR_RR_U0] = { 0xff, U8_8, 0,0,0,0,0 }, - [INSTR_RR_UR] = { 0xff, U4_8,R_12,0,0,0,0 }, - [INSTR_RSE_CCRD] = { 0xff, C_8,C_12,D_20,B_16,0,0 }, - [INSTR_RSE_RRRD] = { 0xff, R_8,R_12,D_20,B_16,0,0 }, - [INSTR_RSE_RURD] = { 0xff, R_8,U4_12,D_20,B_16,0,0 }, - [INSTR_RSI_RRP] = { 0xff, R_8,R_12,J16_16,0,0,0 }, - [INSTR_RSL_R0RD] = { 0xff, D_20,L4_8,B_16,0,0,0 }, - [INSTR_RSY_AARD] = { 0xff, A_8,A_12,D20_20,B_16,0,0 }, - [INSTR_RSY_CCRD] = { 0xff, C_8,C_12,D20_20,B_16,0,0 }, - [INSTR_RSY_RRRD] = { 0xff, R_8,R_12,D20_20,B_16,0,0 }, - [INSTR_RSY_RURD] = { 0xff, R_8,U4_12,D20_20,B_16,0,0 }, - [INSTR_RSY_RDRM] = { 0xff, R_8,D20_20,B_16,U4_12,0,0 }, - [INSTR_RS_AARD] = { 0xff, A_8,A_12,D_20,B_16,0,0 }, - [INSTR_RS_CCRD] = { 0xff, C_8,C_12,D_20,B_16,0,0 }, - [INSTR_RS_R0RD] = { 0xff, R_8,D_20,B_16,0,0,0 }, - [INSTR_RS_RRRD] = { 0xff, R_8,R_12,D_20,B_16,0,0 }, - [INSTR_RS_RURD] = { 0xff, R_8,U4_12,D_20,B_16,0,0 }, - [INSTR_RXE_FRRD] = { 0xff, F_8,D_20,X_12,B_16,0,0 }, - [INSTR_RXE_RRRD] = { 0xff, R_8,D_20,X_12,B_16,0,0 }, - [INSTR_RXF_FRRDF] = { 0xff, F_32,F_8,D_20,X_12,B_16,0 }, - [INSTR_RXY_FRRD] = { 0xff, F_8,D20_20,X_12,B_16,0,0 }, - [INSTR_RXY_RRRD] = { 0xff, R_8,D20_20,X_12,B_16,0,0 }, - [INSTR_RXY_URRD] = { 0xff, U4_8,D20_20,X_12,B_16,0,0 }, - [INSTR_RX_FRRD] = { 0xff, F_8,D_20,X_12,B_16,0,0 }, - [INSTR_RX_RRRD] = { 0xff, R_8,D_20,X_12,B_16,0,0 }, - [INSTR_RX_URRD] = { 0xff, U4_8,D_20,X_12,B_16,0,0 }, - [INSTR_SIL_RDI] = { 0xff, D_20,B_16,I16_32,0,0,0 }, - [INSTR_SIL_RDU] = { 0xff, D_20,B_16,U16_32,0,0,0 }, - [INSTR_SIY_IRD] = { 0xff, D20_20,B_16,I8_8,0,0,0 }, - [INSTR_SIY_URD] = { 0xff, D20_20,B_16,U8_8,0,0,0 }, - [INSTR_SI_URD] = { 0xff, D_20,B_16,U8_8,0,0,0 }, - [INSTR_SSE_RDRD] = { 0xff, D_20,B_16,D_36,B_32,0,0 }, - [INSTR_SSF_RRDRD] = { 0x00, D_20,B_16,D_36,B_32,R_8,0 }, - [INSTR_SSF_RRDRD2]= { 0x00, R_8,D_20,B_16,D_36,B_32,0 }, - [INSTR_SS_L0RDRD] = { 0xff, D_20,L8_8,B_16,D_36,B_32,0 }, - [INSTR_SS_LIRDRD] = { 0xff, D_20,L4_8,B_16,D_36,B_32,U4_12 }, - [INSTR_SS_LLRDRD] = { 0xff, D_20,L4_8,B_16,D_36,L4_12,B_32 }, - [INSTR_SS_RRRDRD2]= { 0xff, R_8,D_20,B_16,R_12,D_36,B_32 }, - [INSTR_SS_RRRDRD3]= { 0xff, R_8,R_12,D_20,B_16,D_36,B_32 }, - [INSTR_SS_RRRDRD] = { 0xff, D_20,R_8,B_16,D_36,B_32,R_12 }, - [INSTR_S_00] = { 0xff, 0,0,0,0,0,0 }, - [INSTR_S_RD] = { 0xff, D_20,B_16,0,0,0,0 }, -}; - -enum { - LONG_INSN_ALGHSIK, - LONG_INSN_ALHSIK, - LONG_INSN_CLFHSI, - LONG_INSN_CLGFRL, - LONG_INSN_CLGHRL, - LONG_INSN_CLGHSI, - LONG_INSN_CLHHSI, - LONG_INSN_LLGFRL, - LONG_INSN_LLGHRL, - LONG_INSN_POPCNT, - LONG_INSN_RISBHG, - LONG_INSN_RISBLG, -}; - -static char *long_insn_name[] = { - [LONG_INSN_ALGHSIK] = "alghsik", - [LONG_INSN_ALHSIK] = "alhsik", - [LONG_INSN_CLFHSI] = "clfhsi", - [LONG_INSN_CLGFRL] = "clgfrl", - [LONG_INSN_CLGHRL] = "clghrl", - [LONG_INSN_CLGHSI] = "clghsi", - [LONG_INSN_CLHHSI] = "clhhsi", - [LONG_INSN_LLGFRL] = "llgfrl", - [LONG_INSN_LLGHRL] = "llghrl", - [LONG_INSN_POPCNT] = "popcnt", - [LONG_INSN_RISBHG] = "risbhg", - [LONG_INSN_RISBLG] = "risblk", -}; - -static struct insn opcode[] = { -#ifdef CONFIG_64BIT - { "lmd", 0xef, INSTR_SS_RRRDRD3 }, -#endif - { "spm", 0x04, INSTR_RR_R0 }, - { "balr", 0x05, INSTR_RR_RR }, - { "bctr", 0x06, INSTR_RR_RR }, - { "bcr", 0x07, INSTR_RR_UR }, - { "svc", 0x0a, INSTR_RR_U0 }, - { "bsm", 0x0b, INSTR_RR_RR }, - { "bassm", 0x0c, INSTR_RR_RR }, - { "basr", 0x0d, INSTR_RR_RR }, - { "mvcl", 0x0e, INSTR_RR_RR }, - { "clcl", 0x0f, INSTR_RR_RR }, - { "lpr", 0x10, INSTR_RR_RR }, - { "lnr", 0x11, INSTR_RR_RR }, - { "ltr", 0x12, INSTR_RR_RR }, - { "lcr", 0x13, INSTR_RR_RR }, - { "nr", 0x14, INSTR_RR_RR }, - { "clr", 0x15, INSTR_RR_RR }, - { "or", 0x16, INSTR_RR_RR }, - { "xr", 0x17, INSTR_RR_RR }, - { "lr", 0x18, INSTR_RR_RR }, - { "cr", 0x19, INSTR_RR_RR }, - { "ar", 0x1a, INSTR_RR_RR }, - { "sr", 0x1b, INSTR_RR_RR }, - { "mr", 0x1c, INSTR_RR_RR }, - { "dr", 0x1d, INSTR_RR_RR }, - { "alr", 0x1e, INSTR_RR_RR }, - { "slr", 0x1f, INSTR_RR_RR }, - { "lpdr", 0x20, INSTR_RR_FF }, - { "lndr", 0x21, INSTR_RR_FF }, - { "ltdr", 0x22, INSTR_RR_FF }, - { "lcdr", 0x23, INSTR_RR_FF }, - { "hdr", 0x24, INSTR_RR_FF }, - { "ldxr", 0x25, INSTR_RR_FF }, - { "lrdr", 0x25, INSTR_RR_FF }, - { "mxr", 0x26, INSTR_RR_FF }, - { "mxdr", 0x27, INSTR_RR_FF }, - { "ldr", 0x28, INSTR_RR_FF }, - { "cdr", 0x29, INSTR_RR_FF }, - { "adr", 0x2a, INSTR_RR_FF }, - { "sdr", 0x2b, INSTR_RR_FF }, - { "mdr", 0x2c, INSTR_RR_FF }, - { "ddr", 0x2d, INSTR_RR_FF }, - { "awr", 0x2e, INSTR_RR_FF }, - { "swr", 0x2f, INSTR_RR_FF }, - { "lper", 0x30, INSTR_RR_FF }, - { "lner", 0x31, INSTR_RR_FF }, - { "lter", 0x32, INSTR_RR_FF }, - { "lcer", 0x33, INSTR_RR_FF }, - { "her", 0x34, INSTR_RR_FF }, - { "ledr", 0x35, INSTR_RR_FF }, - { "lrer", 0x35, INSTR_RR_FF }, - { "axr", 0x36, INSTR_RR_FF }, - { "sxr", 0x37, INSTR_RR_FF }, - { "ler", 0x38, INSTR_RR_FF }, - { "cer", 0x39, INSTR_RR_FF }, - { "aer", 0x3a, INSTR_RR_FF }, - { "ser", 0x3b, INSTR_RR_FF }, - { "mder", 0x3c, INSTR_RR_FF }, - { "mer", 0x3c, INSTR_RR_FF }, - { "der", 0x3d, INSTR_RR_FF }, - { "aur", 0x3e, INSTR_RR_FF }, - { "sur", 0x3f, INSTR_RR_FF }, - { "sth", 0x40, INSTR_RX_RRRD }, - { "la", 0x41, INSTR_RX_RRRD }, - { "stc", 0x42, INSTR_RX_RRRD }, - { "ic", 0x43, INSTR_RX_RRRD }, - { "ex", 0x44, INSTR_RX_RRRD }, - { "bal", 0x45, INSTR_RX_RRRD }, - { "bct", 0x46, INSTR_RX_RRRD }, - { "bc", 0x47, INSTR_RX_URRD }, - { "lh", 0x48, INSTR_RX_RRRD }, - { "ch", 0x49, INSTR_RX_RRRD }, - { "ah", 0x4a, INSTR_RX_RRRD }, - { "sh", 0x4b, INSTR_RX_RRRD }, - { "mh", 0x4c, INSTR_RX_RRRD }, - { "bas", 0x4d, INSTR_RX_RRRD }, - { "cvd", 0x4e, INSTR_RX_RRRD }, - { "cvb", 0x4f, INSTR_RX_RRRD }, - { "st", 0x50, INSTR_RX_RRRD }, - { "lae", 0x51, INSTR_RX_RRRD }, - { "n", 0x54, INSTR_RX_RRRD }, - { "cl", 0x55, INSTR_RX_RRRD }, - { "o", 0x56, INSTR_RX_RRRD }, - { "x", 0x57, INSTR_RX_RRRD }, - { "l", 0x58, INSTR_RX_RRRD }, - { "c", 0x59, INSTR_RX_RRRD }, - { "a", 0x5a, INSTR_RX_RRRD }, - { "s", 0x5b, INSTR_RX_RRRD }, - { "m", 0x5c, INSTR_RX_RRRD }, - { "d", 0x5d, INSTR_RX_RRRD }, - { "al", 0x5e, INSTR_RX_RRRD }, - { "sl", 0x5f, INSTR_RX_RRRD }, - { "std", 0x60, INSTR_RX_FRRD }, - { "mxd", 0x67, INSTR_RX_FRRD }, - { "ld", 0x68, INSTR_RX_FRRD }, - { "cd", 0x69, INSTR_RX_FRRD }, - { "ad", 0x6a, INSTR_RX_FRRD }, - { "sd", 0x6b, INSTR_RX_FRRD }, - { "md", 0x6c, INSTR_RX_FRRD }, - { "dd", 0x6d, INSTR_RX_FRRD }, - { "aw", 0x6e, INSTR_RX_FRRD }, - { "sw", 0x6f, INSTR_RX_FRRD }, - { "ste", 0x70, INSTR_RX_FRRD }, - { "ms", 0x71, INSTR_RX_RRRD }, - { "le", 0x78, INSTR_RX_FRRD }, - { "ce", 0x79, INSTR_RX_FRRD }, - { "ae", 0x7a, INSTR_RX_FRRD }, - { "se", 0x7b, INSTR_RX_FRRD }, - { "mde", 0x7c, INSTR_RX_FRRD }, - { "me", 0x7c, INSTR_RX_FRRD }, - { "de", 0x7d, INSTR_RX_FRRD }, - { "au", 0x7e, INSTR_RX_FRRD }, - { "su", 0x7f, INSTR_RX_FRRD }, - { "ssm", 0x80, INSTR_S_RD }, - { "lpsw", 0x82, INSTR_S_RD }, - { "diag", 0x83, INSTR_RS_RRRD }, - { "brxh", 0x84, INSTR_RSI_RRP }, - { "brxle", 0x85, INSTR_RSI_RRP }, - { "bxh", 0x86, INSTR_RS_RRRD }, - { "bxle", 0x87, INSTR_RS_RRRD }, - { "srl", 0x88, INSTR_RS_R0RD }, - { "sll", 0x89, INSTR_RS_R0RD }, - { "sra", 0x8a, INSTR_RS_R0RD }, - { "sla", 0x8b, INSTR_RS_R0RD }, - { "srdl", 0x8c, INSTR_RS_R0RD }, - { "sldl", 0x8d, INSTR_RS_R0RD }, - { "srda", 0x8e, INSTR_RS_R0RD }, - { "slda", 0x8f, INSTR_RS_R0RD }, - { "stm", 0x90, INSTR_RS_RRRD }, - { "tm", 0x91, INSTR_SI_URD }, - { "mvi", 0x92, INSTR_SI_URD }, - { "ts", 0x93, INSTR_S_RD }, - { "ni", 0x94, INSTR_SI_URD }, - { "cli", 0x95, INSTR_SI_URD }, - { "oi", 0x96, INSTR_SI_URD }, - { "xi", 0x97, INSTR_SI_URD }, - { "lm", 0x98, INSTR_RS_RRRD }, - { "trace", 0x99, INSTR_RS_RRRD }, - { "lam", 0x9a, INSTR_RS_AARD }, - { "stam", 0x9b, INSTR_RS_AARD }, - { "mvcle", 0xa8, INSTR_RS_RRRD }, - { "clcle", 0xa9, INSTR_RS_RRRD }, - { "stnsm", 0xac, INSTR_SI_URD }, - { "stosm", 0xad, INSTR_SI_URD }, - { "sigp", 0xae, INSTR_RS_RRRD }, - { "mc", 0xaf, INSTR_SI_URD }, - { "lra", 0xb1, INSTR_RX_RRRD }, - { "stctl", 0xb6, INSTR_RS_CCRD }, - { "lctl", 0xb7, INSTR_RS_CCRD }, - { "cs", 0xba, INSTR_RS_RRRD }, - { "cds", 0xbb, INSTR_RS_RRRD }, - { "clm", 0xbd, INSTR_RS_RURD }, - { "stcm", 0xbe, INSTR_RS_RURD }, - { "icm", 0xbf, INSTR_RS_RURD }, - { "mvn", 0xd1, INSTR_SS_L0RDRD }, - { "mvc", 0xd2, INSTR_SS_L0RDRD }, - { "mvz", 0xd3, INSTR_SS_L0RDRD }, - { "nc", 0xd4, INSTR_SS_L0RDRD }, - { "clc", 0xd5, INSTR_SS_L0RDRD }, - { "oc", 0xd6, INSTR_SS_L0RDRD }, - { "xc", 0xd7, INSTR_SS_L0RDRD }, - { "mvck", 0xd9, INSTR_SS_RRRDRD }, - { "mvcp", 0xda, INSTR_SS_RRRDRD }, - { "mvcs", 0xdb, INSTR_SS_RRRDRD }, - { "tr", 0xdc, INSTR_SS_L0RDRD }, - { "trt", 0xdd, INSTR_SS_L0RDRD }, - { "ed", 0xde, INSTR_SS_L0RDRD }, - { "edmk", 0xdf, INSTR_SS_L0RDRD }, - { "pku", 0xe1, INSTR_SS_L0RDRD }, - { "unpku", 0xe2, INSTR_SS_L0RDRD }, - { "mvcin", 0xe8, INSTR_SS_L0RDRD }, - { "pka", 0xe9, INSTR_SS_L0RDRD }, - { "unpka", 0xea, INSTR_SS_L0RDRD }, - { "plo", 0xee, INSTR_SS_RRRDRD2 }, - { "srp", 0xf0, INSTR_SS_LIRDRD }, - { "mvo", 0xf1, INSTR_SS_LLRDRD }, - { "pack", 0xf2, INSTR_SS_LLRDRD }, - { "unpk", 0xf3, INSTR_SS_LLRDRD }, - { "zap", 0xf8, INSTR_SS_LLRDRD }, - { "cp", 0xf9, INSTR_SS_LLRDRD }, - { "ap", 0xfa, INSTR_SS_LLRDRD }, - { "sp", 0xfb, INSTR_SS_LLRDRD }, - { "mp", 0xfc, INSTR_SS_LLRDRD }, - { "dp", 0xfd, INSTR_SS_LLRDRD }, - { "", 0, INSTR_INVALID } -}; - -static struct insn opcode_01[] = { -#ifdef CONFIG_64BIT - { "sam64", 0x0e, INSTR_E }, - { "pfpo", 0x0a, INSTR_E }, - { "ptff", 0x04, INSTR_E }, -#endif - { "pr", 0x01, INSTR_E }, - { "upt", 0x02, INSTR_E }, - { "sckpf", 0x07, INSTR_E }, - { "tam", 0x0b, INSTR_E }, - { "sam24", 0x0c, INSTR_E }, - { "sam31", 0x0d, INSTR_E }, - { "trap2", 0xff, INSTR_E }, - { "", 0, INSTR_INVALID } -}; - -static struct insn opcode_a5[] = { -#ifdef CONFIG_64BIT - { "iihh", 0x00, INSTR_RI_RU }, - { "iihl", 0x01, INSTR_RI_RU }, - { "iilh", 0x02, INSTR_RI_RU }, - { "iill", 0x03, INSTR_RI_RU }, - { "nihh", 0x04, INSTR_RI_RU }, - { "nihl", 0x05, INSTR_RI_RU }, - { "nilh", 0x06, INSTR_RI_RU }, - { "nill", 0x07, INSTR_RI_RU }, - { "oihh", 0x08, INSTR_RI_RU }, - { "oihl", 0x09, INSTR_RI_RU }, - { "oilh", 0x0a, INSTR_RI_RU }, - { "oill", 0x0b, INSTR_RI_RU }, - { "llihh", 0x0c, INSTR_RI_RU }, - { "llihl", 0x0d, INSTR_RI_RU }, - { "llilh", 0x0e, INSTR_RI_RU }, - { "llill", 0x0f, INSTR_RI_RU }, -#endif - { "", 0, INSTR_INVALID } -}; - -static struct insn opcode_a7[] = { -#ifdef CONFIG_64BIT - { "tmhh", 0x02, INSTR_RI_RU }, - { "tmhl", 0x03, INSTR_RI_RU }, - { "brctg", 0x07, INSTR_RI_RP }, - { "lghi", 0x09, INSTR_RI_RI }, - { "aghi", 0x0b, INSTR_RI_RI }, - { "mghi", 0x0d, INSTR_RI_RI }, - { "cghi", 0x0f, INSTR_RI_RI }, -#endif - { "tmlh", 0x00, INSTR_RI_RU }, - { "tmll", 0x01, INSTR_RI_RU }, - { "brc", 0x04, INSTR_RI_UP }, - { "bras", 0x05, INSTR_RI_RP }, - { "brct", 0x06, INSTR_RI_RP }, - { "lhi", 0x08, INSTR_RI_RI }, - { "ahi", 0x0a, INSTR_RI_RI }, - { "mhi", 0x0c, INSTR_RI_RI }, - { "chi", 0x0e, INSTR_RI_RI }, - { "", 0, INSTR_INVALID } -}; - -static struct insn opcode_b2[] = { -#ifdef CONFIG_64BIT - { "sske", 0x2b, INSTR_RRF_M0RR }, - { "stckf", 0x7c, INSTR_S_RD }, - { "cu21", 0xa6, INSTR_RRF_M0RR }, - { "cuutf", 0xa6, INSTR_RRF_M0RR }, - { "cu12", 0xa7, INSTR_RRF_M0RR }, - { "cutfu", 0xa7, INSTR_RRF_M0RR }, - { "stfle", 0xb0, INSTR_S_RD }, - { "lpswe", 0xb2, INSTR_S_RD }, - { "srnmt", 0xb9, INSTR_S_RD }, - { "lfas", 0xbd, INSTR_S_RD }, -#endif - { "stidp", 0x02, INSTR_S_RD }, - { "sck", 0x04, INSTR_S_RD }, - { "stck", 0x05, INSTR_S_RD }, - { "sckc", 0x06, INSTR_S_RD }, - { "stckc", 0x07, INSTR_S_RD }, - { "spt", 0x08, INSTR_S_RD }, - { "stpt", 0x09, INSTR_S_RD }, - { "spka", 0x0a, INSTR_S_RD }, - { "ipk", 0x0b, INSTR_S_00 }, - { "ptlb", 0x0d, INSTR_S_00 }, - { "spx", 0x10, INSTR_S_RD }, - { "stpx", 0x11, INSTR_S_RD }, - { "stap", 0x12, INSTR_S_RD }, - { "sie", 0x14, INSTR_S_RD }, - { "pc", 0x18, INSTR_S_RD }, - { "sac", 0x19, INSTR_S_RD }, - { "cfc", 0x1a, INSTR_S_RD }, - { "ipte", 0x21, INSTR_RRE_RR }, - { "ipm", 0x22, INSTR_RRE_R0 }, - { "ivsk", 0x23, INSTR_RRE_RR }, - { "iac", 0x24, INSTR_RRE_R0 }, - { "ssar", 0x25, INSTR_RRE_R0 }, - { "epar", 0x26, INSTR_RRE_R0 }, - { "esar", 0x27, INSTR_RRE_R0 }, - { "pt", 0x28, INSTR_RRE_RR }, - { "iske", 0x29, INSTR_RRE_RR }, - { "rrbe", 0x2a, INSTR_RRE_RR }, - { "sske", 0x2b, INSTR_RRE_RR }, - { "tb", 0x2c, INSTR_RRE_0R }, - { "dxr", 0x2d, INSTR_RRE_F0 }, - { "pgin", 0x2e, INSTR_RRE_RR }, - { "pgout", 0x2f, INSTR_RRE_RR }, - { "csch", 0x30, INSTR_S_00 }, - { "hsch", 0x31, INSTR_S_00 }, - { "msch", 0x32, INSTR_S_RD }, - { "ssch", 0x33, INSTR_S_RD }, - { "stsch", 0x34, INSTR_S_RD }, - { "tsch", 0x35, INSTR_S_RD }, - { "tpi", 0x36, INSTR_S_RD }, - { "sal", 0x37, INSTR_S_00 }, - { "rsch", 0x38, INSTR_S_00 }, - { "stcrw", 0x39, INSTR_S_RD }, - { "stcps", 0x3a, INSTR_S_RD }, - { "rchp", 0x3b, INSTR_S_00 }, - { "schm", 0x3c, INSTR_S_00 }, - { "bakr", 0x40, INSTR_RRE_RR }, - { "cksm", 0x41, INSTR_RRE_RR }, - { "sqdr", 0x44, INSTR_RRE_F0 }, - { "sqer", 0x45, INSTR_RRE_F0 }, - { "stura", 0x46, INSTR_RRE_RR }, - { "msta", 0x47, INSTR_RRE_R0 }, - { "palb", 0x48, INSTR_RRE_00 }, - { "ereg", 0x49, INSTR_RRE_RR }, - { "esta", 0x4a, INSTR_RRE_RR }, - { "lura", 0x4b, INSTR_RRE_RR }, - { "tar", 0x4c, INSTR_RRE_AR }, - { "cpya", 0x4d, INSTR_RRE_AA }, - { "sar", 0x4e, INSTR_RRE_AR }, - { "ear", 0x4f, INSTR_RRE_RA }, - { "csp", 0x50, INSTR_RRE_RR }, - { "msr", 0x52, INSTR_RRE_RR }, - { "mvpg", 0x54, INSTR_RRE_RR }, - { "mvst", 0x55, INSTR_RRE_RR }, - { "cuse", 0x57, INSTR_RRE_RR }, - { "bsg", 0x58, INSTR_RRE_RR }, - { "bsa", 0x5a, INSTR_RRE_RR }, - { "clst", 0x5d, INSTR_RRE_RR }, - { "srst", 0x5e, INSTR_RRE_RR }, - { "cmpsc", 0x63, INSTR_RRE_RR }, - { "siga", 0x74, INSTR_S_RD }, - { "xsch", 0x76, INSTR_S_00 }, - { "rp", 0x77, INSTR_S_RD }, - { "stcke", 0x78, INSTR_S_RD }, - { "sacf", 0x79, INSTR_S_RD }, - { "spp", 0x80, INSTR_S_RD }, - { "stsi", 0x7d, INSTR_S_RD }, - { "srnm", 0x99, INSTR_S_RD }, - { "stfpc", 0x9c, INSTR_S_RD }, - { "lfpc", 0x9d, INSTR_S_RD }, - { "tre", 0xa5, INSTR_RRE_RR }, - { "cuutf", 0xa6, INSTR_RRE_RR }, - { "cutfu", 0xa7, INSTR_RRE_RR }, - { "stfl", 0xb1, INSTR_S_RD }, - { "trap4", 0xff, INSTR_S_RD }, - { "", 0, INSTR_INVALID } -}; - -static struct insn opcode_b3[] = { -#ifdef CONFIG_64BIT - { "maylr", 0x38, INSTR_RRF_F0FF }, - { "mylr", 0x39, INSTR_RRF_F0FF }, - { "mayr", 0x3a, INSTR_RRF_F0FF }, - { "myr", 0x3b, INSTR_RRF_F0FF }, - { "mayhr", 0x3c, INSTR_RRF_F0FF }, - { "myhr", 0x3d, INSTR_RRF_F0FF }, - { "cegbr", 0xa4, INSTR_RRE_RR }, - { "cdgbr", 0xa5, INSTR_RRE_RR }, - { "cxgbr", 0xa6, INSTR_RRE_RR }, - { "cgebr", 0xa8, INSTR_RRF_U0RF }, - { "cgdbr", 0xa9, INSTR_RRF_U0RF }, - { "cgxbr", 0xaa, INSTR_RRF_U0RF }, - { "cfer", 0xb8, INSTR_RRF_U0RF }, - { "cfdr", 0xb9, INSTR_RRF_U0RF }, - { "cfxr", 0xba, INSTR_RRF_U0RF }, - { "cegr", 0xc4, INSTR_RRE_RR }, - { "cdgr", 0xc5, INSTR_RRE_RR }, - { "cxgr", 0xc6, INSTR_RRE_RR }, - { "cger", 0xc8, INSTR_RRF_U0RF }, - { "cgdr", 0xc9, INSTR_RRF_U0RF }, - { "cgxr", 0xca, INSTR_RRF_U0RF }, - { "lpdfr", 0x70, INSTR_RRE_FF }, - { "lndfr", 0x71, INSTR_RRE_FF }, - { "cpsdr", 0x72, INSTR_RRF_F0FF2 }, - { "lcdfr", 0x73, INSTR_RRE_FF }, - { "ldgr", 0xc1, INSTR_RRE_FR }, - { "lgdr", 0xcd, INSTR_RRE_RF }, - { "adtr", 0xd2, INSTR_RRR_F0FF }, - { "axtr", 0xda, INSTR_RRR_F0FF }, - { "cdtr", 0xe4, INSTR_RRE_FF }, - { "cxtr", 0xec, INSTR_RRE_FF }, - { "kdtr", 0xe0, INSTR_RRE_FF }, - { "kxtr", 0xe8, INSTR_RRE_FF }, - { "cedtr", 0xf4, INSTR_RRE_FF }, - { "cextr", 0xfc, INSTR_RRE_FF }, - { "cdgtr", 0xf1, INSTR_RRE_FR }, - { "cxgtr", 0xf9, INSTR_RRE_FR }, - { "cdstr", 0xf3, INSTR_RRE_FR }, - { "cxstr", 0xfb, INSTR_RRE_FR }, - { "cdutr", 0xf2, INSTR_RRE_FR }, - { "cxutr", 0xfa, INSTR_RRE_FR }, - { "cgdtr", 0xe1, INSTR_RRF_U0RF }, - { "cgxtr", 0xe9, INSTR_RRF_U0RF }, - { "csdtr", 0xe3, INSTR_RRE_RF }, - { "csxtr", 0xeb, INSTR_RRE_RF }, - { "cudtr", 0xe2, INSTR_RRE_RF }, - { "cuxtr", 0xea, INSTR_RRE_RF }, - { "ddtr", 0xd1, INSTR_RRR_F0FF }, - { "dxtr", 0xd9, INSTR_RRR_F0FF }, - { "eedtr", 0xe5, INSTR_RRE_RF }, - { "eextr", 0xed, INSTR_RRE_RF }, - { "esdtr", 0xe7, INSTR_RRE_RF }, - { "esxtr", 0xef, INSTR_RRE_RF }, - { "iedtr", 0xf6, INSTR_RRF_F0FR }, - { "iextr", 0xfe, INSTR_RRF_F0FR }, - { "ltdtr", 0xd6, INSTR_RRE_FF }, - { "ltxtr", 0xde, INSTR_RRE_FF }, - { "fidtr", 0xd7, INSTR_RRF_UUFF }, - { "fixtr", 0xdf, INSTR_RRF_UUFF }, - { "ldetr", 0xd4, INSTR_RRF_0UFF }, - { "lxdtr", 0xdc, INSTR_RRF_0UFF }, - { "ledtr", 0xd5, INSTR_RRF_UUFF }, - { "ldxtr", 0xdd, INSTR_RRF_UUFF }, - { "mdtr", 0xd0, INSTR_RRR_F0FF }, - { "mxtr", 0xd8, INSTR_RRR_F0FF }, - { "qadtr", 0xf5, INSTR_RRF_FUFF }, - { "qaxtr", 0xfd, INSTR_RRF_FUFF }, - { "rrdtr", 0xf7, INSTR_RRF_FFRU }, - { "rrxtr", 0xff, INSTR_RRF_FFRU }, - { "sfasr", 0x85, INSTR_RRE_R0 }, - { "sdtr", 0xd3, INSTR_RRR_F0FF }, - { "sxtr", 0xdb, INSTR_RRR_F0FF }, -#endif - { "lpebr", 0x00, INSTR_RRE_FF }, - { "lnebr", 0x01, INSTR_RRE_FF }, - { "ltebr", 0x02, INSTR_RRE_FF }, - { "lcebr", 0x03, INSTR_RRE_FF }, - { "ldebr", 0x04, INSTR_RRE_FF }, - { "lxdbr", 0x05, INSTR_RRE_FF }, - { "lxebr", 0x06, INSTR_RRE_FF }, - { "mxdbr", 0x07, INSTR_RRE_FF }, - { "kebr", 0x08, INSTR_RRE_FF }, - { "cebr", 0x09, INSTR_RRE_FF }, - { "aebr", 0x0a, INSTR_RRE_FF }, - { "sebr", 0x0b, INSTR_RRE_FF }, - { "mdebr", 0x0c, INSTR_RRE_FF }, - { "debr", 0x0d, INSTR_RRE_FF }, - { "maebr", 0x0e, INSTR_RRF_F0FF }, - { "msebr", 0x0f, INSTR_RRF_F0FF }, - { "lpdbr", 0x10, INSTR_RRE_FF }, - { "lndbr", 0x11, INSTR_RRE_FF }, - { "ltdbr", 0x12, INSTR_RRE_FF }, - { "lcdbr", 0x13, INSTR_RRE_FF }, - { "sqebr", 0x14, INSTR_RRE_FF }, - { "sqdbr", 0x15, INSTR_RRE_FF }, - { "sqxbr", 0x16, INSTR_RRE_FF }, - { "meebr", 0x17, INSTR_RRE_FF }, - { "kdbr", 0x18, INSTR_RRE_FF }, - { "cdbr", 0x19, INSTR_RRE_FF }, - { "adbr", 0x1a, INSTR_RRE_FF }, - { "sdbr", 0x1b, INSTR_RRE_FF }, - { "mdbr", 0x1c, INSTR_RRE_FF }, - { "ddbr", 0x1d, INSTR_RRE_FF }, - { "madbr", 0x1e, INSTR_RRF_F0FF }, - { "msdbr", 0x1f, INSTR_RRF_F0FF }, - { "lder", 0x24, INSTR_RRE_FF }, - { "lxdr", 0x25, INSTR_RRE_FF }, - { "lxer", 0x26, INSTR_RRE_FF }, - { "maer", 0x2e, INSTR_RRF_F0FF }, - { "mser", 0x2f, INSTR_RRF_F0FF }, - { "sqxr", 0x36, INSTR_RRE_FF }, - { "meer", 0x37, INSTR_RRE_FF }, - { "madr", 0x3e, INSTR_RRF_F0FF }, - { "msdr", 0x3f, INSTR_RRF_F0FF }, - { "lpxbr", 0x40, INSTR_RRE_FF }, - { "lnxbr", 0x41, INSTR_RRE_FF }, - { "ltxbr", 0x42, INSTR_RRE_FF }, - { "lcxbr", 0x43, INSTR_RRE_FF }, - { "ledbr", 0x44, INSTR_RRE_FF }, - { "ldxbr", 0x45, INSTR_RRE_FF }, - { "lexbr", 0x46, INSTR_RRE_FF }, - { "fixbr", 0x47, INSTR_RRF_U0FF }, - { "kxbr", 0x48, INSTR_RRE_FF }, - { "cxbr", 0x49, INSTR_RRE_FF }, - { "axbr", 0x4a, INSTR_RRE_FF }, - { "sxbr", 0x4b, INSTR_RRE_FF }, - { "mxbr", 0x4c, INSTR_RRE_FF }, - { "dxbr", 0x4d, INSTR_RRE_FF }, - { "tbedr", 0x50, INSTR_RRF_U0FF }, - { "tbdr", 0x51, INSTR_RRF_U0FF }, - { "diebr", 0x53, INSTR_RRF_FUFF }, - { "fiebr", 0x57, INSTR_RRF_U0FF }, - { "thder", 0x58, INSTR_RRE_RR }, - { "thdr", 0x59, INSTR_RRE_RR }, - { "didbr", 0x5b, INSTR_RRF_FUFF }, - { "fidbr", 0x5f, INSTR_RRF_U0FF }, - { "lpxr", 0x60, INSTR_RRE_FF }, - { "lnxr", 0x61, INSTR_RRE_FF }, - { "ltxr", 0x62, INSTR_RRE_FF }, - { "lcxr", 0x63, INSTR_RRE_FF }, - { "lxr", 0x65, INSTR_RRE_RR }, - { "lexr", 0x66, INSTR_RRE_FF }, - { "fixr", 0x67, INSTR_RRF_U0FF }, - { "cxr", 0x69, INSTR_RRE_FF }, - { "lzer", 0x74, INSTR_RRE_R0 }, - { "lzdr", 0x75, INSTR_RRE_R0 }, - { "lzxr", 0x76, INSTR_RRE_R0 }, - { "fier", 0x77, INSTR_RRF_U0FF }, - { "fidr", 0x7f, INSTR_RRF_U0FF }, - { "sfpc", 0x84, INSTR_RRE_RR_OPT }, - { "efpc", 0x8c, INSTR_RRE_RR_OPT }, - { "cefbr", 0x94, INSTR_RRE_RF }, - { "cdfbr", 0x95, INSTR_RRE_RF }, - { "cxfbr", 0x96, INSTR_RRE_RF }, - { "cfebr", 0x98, INSTR_RRF_U0RF }, - { "cfdbr", 0x99, INSTR_RRF_U0RF }, - { "cfxbr", 0x9a, INSTR_RRF_U0RF }, - { "cefr", 0xb4, INSTR_RRE_RF }, - { "cdfr", 0xb5, INSTR_RRE_RF }, - { "cxfr", 0xb6, INSTR_RRE_RF }, - { "", 0, INSTR_INVALID } -}; - -static struct insn opcode_b9[] = { -#ifdef CONFIG_64BIT - { "lpgr", 0x00, INSTR_RRE_RR }, - { "lngr", 0x01, INSTR_RRE_RR }, - { "ltgr", 0x02, INSTR_RRE_RR }, - { "lcgr", 0x03, INSTR_RRE_RR }, - { "lgr", 0x04, INSTR_RRE_RR }, - { "lurag", 0x05, INSTR_RRE_RR }, - { "lgbr", 0x06, INSTR_RRE_RR }, - { "lghr", 0x07, INSTR_RRE_RR }, - { "agr", 0x08, INSTR_RRE_RR }, - { "sgr", 0x09, INSTR_RRE_RR }, - { "algr", 0x0a, INSTR_RRE_RR }, - { "slgr", 0x0b, INSTR_RRE_RR }, - { "msgr", 0x0c, INSTR_RRE_RR }, - { "dsgr", 0x0d, INSTR_RRE_RR }, - { "eregg", 0x0e, INSTR_RRE_RR }, - { "lrvgr", 0x0f, INSTR_RRE_RR }, - { "lpgfr", 0x10, INSTR_RRE_RR }, - { "lngfr", 0x11, INSTR_RRE_RR }, - { "ltgfr", 0x12, INSTR_RRE_RR }, - { "lcgfr", 0x13, INSTR_RRE_RR }, - { "lgfr", 0x14, INSTR_RRE_RR }, - { "llgfr", 0x16, INSTR_RRE_RR }, - { "llgtr", 0x17, INSTR_RRE_RR }, - { "agfr", 0x18, INSTR_RRE_RR }, - { "sgfr", 0x19, INSTR_RRE_RR }, - { "algfr", 0x1a, INSTR_RRE_RR }, - { "slgfr", 0x1b, INSTR_RRE_RR }, - { "msgfr", 0x1c, INSTR_RRE_RR }, - { "dsgfr", 0x1d, INSTR_RRE_RR }, - { "cgr", 0x20, INSTR_RRE_RR }, - { "clgr", 0x21, INSTR_RRE_RR }, - { "sturg", 0x25, INSTR_RRE_RR }, - { "lbr", 0x26, INSTR_RRE_RR }, - { "lhr", 0x27, INSTR_RRE_RR }, - { "cgfr", 0x30, INSTR_RRE_RR }, - { "clgfr", 0x31, INSTR_RRE_RR }, - { "bctgr", 0x46, INSTR_RRE_RR }, - { "ngr", 0x80, INSTR_RRE_RR }, - { "ogr", 0x81, INSTR_RRE_RR }, - { "xgr", 0x82, INSTR_RRE_RR }, - { "flogr", 0x83, INSTR_RRE_RR }, - { "llgcr", 0x84, INSTR_RRE_RR }, - { "llghr", 0x85, INSTR_RRE_RR }, - { "mlgr", 0x86, INSTR_RRE_RR }, - { "dlgr", 0x87, INSTR_RRE_RR }, - { "alcgr", 0x88, INSTR_RRE_RR }, - { "slbgr", 0x89, INSTR_RRE_RR }, - { "cspg", 0x8a, INSTR_RRE_RR }, - { "idte", 0x8e, INSTR_RRF_R0RR }, - { "llcr", 0x94, INSTR_RRE_RR }, - { "llhr", 0x95, INSTR_RRE_RR }, - { "esea", 0x9d, INSTR_RRE_R0 }, - { "lptea", 0xaa, INSTR_RRF_RURR }, - { "cu14", 0xb0, INSTR_RRF_M0RR }, - { "cu24", 0xb1, INSTR_RRF_M0RR }, - { "cu41", 0xb2, INSTR_RRF_M0RR }, - { "cu42", 0xb3, INSTR_RRF_M0RR }, - { "crt", 0x72, INSTR_RRF_U0RR }, - { "cgrt", 0x60, INSTR_RRF_U0RR }, - { "clrt", 0x73, INSTR_RRF_U0RR }, - { "clgrt", 0x61, INSTR_RRF_U0RR }, - { "ptf", 0xa2, INSTR_RRE_R0 }, - { "pfmf", 0xaf, INSTR_RRE_RR }, - { "trte", 0xbf, INSTR_RRF_M0RR }, - { "trtre", 0xbd, INSTR_RRF_M0RR }, - { "ahhhr", 0xc8, INSTR_RRF_R0RR2 }, - { "shhhr", 0xc9, INSTR_RRF_R0RR2 }, - { "alhhh", 0xca, INSTR_RRF_R0RR2 }, - { "alhhl", 0xca, INSTR_RRF_R0RR2 }, - { "slhhh", 0xcb, INSTR_RRF_R0RR2 }, - { "chhr ", 0xcd, INSTR_RRE_RR }, - { "clhhr", 0xcf, INSTR_RRE_RR }, - { "ahhlr", 0xd8, INSTR_RRF_R0RR2 }, - { "shhlr", 0xd9, INSTR_RRF_R0RR2 }, - { "slhhl", 0xdb, INSTR_RRF_R0RR2 }, - { "chlr", 0xdd, INSTR_RRE_RR }, - { "clhlr", 0xdf, INSTR_RRE_RR }, - { { 0, LONG_INSN_POPCNT }, 0xe1, INSTR_RRE_RR }, - { "locgr", 0xe2, INSTR_RRF_M0RR }, - { "ngrk", 0xe4, INSTR_RRF_R0RR2 }, - { "ogrk", 0xe6, INSTR_RRF_R0RR2 }, - { "xgrk", 0xe7, INSTR_RRF_R0RR2 }, - { "agrk", 0xe8, INSTR_RRF_R0RR2 }, - { "sgrk", 0xe9, INSTR_RRF_R0RR2 }, - { "algrk", 0xea, INSTR_RRF_R0RR2 }, - { "slgrk", 0xeb, INSTR_RRF_R0RR2 }, - { "locr", 0xf2, INSTR_RRF_M0RR }, - { "nrk", 0xf4, INSTR_RRF_R0RR2 }, - { "ork", 0xf6, INSTR_RRF_R0RR2 }, - { "xrk", 0xf7, INSTR_RRF_R0RR2 }, - { "ark", 0xf8, INSTR_RRF_R0RR2 }, - { "srk", 0xf9, INSTR_RRF_R0RR2 }, - { "alrk", 0xfa, INSTR_RRF_R0RR2 }, - { "slrk", 0xfb, INSTR_RRF_R0RR2 }, -#endif - { "kmac", 0x1e, INSTR_RRE_RR }, - { "lrvr", 0x1f, INSTR_RRE_RR }, - { "km", 0x2e, INSTR_RRE_RR }, - { "kmc", 0x2f, INSTR_RRE_RR }, - { "kimd", 0x3e, INSTR_RRE_RR }, - { "klmd", 0x3f, INSTR_RRE_RR }, - { "epsw", 0x8d, INSTR_RRE_RR }, - { "trtt", 0x90, INSTR_RRE_RR }, - { "trtt", 0x90, INSTR_RRF_M0RR }, - { "trto", 0x91, INSTR_RRE_RR }, - { "trto", 0x91, INSTR_RRF_M0RR }, - { "trot", 0x92, INSTR_RRE_RR }, - { "trot", 0x92, INSTR_RRF_M0RR }, - { "troo", 0x93, INSTR_RRE_RR }, - { "troo", 0x93, INSTR_RRF_M0RR }, - { "mlr", 0x96, INSTR_RRE_RR }, - { "dlr", 0x97, INSTR_RRE_RR }, - { "alcr", 0x98, INSTR_RRE_RR }, - { "slbr", 0x99, INSTR_RRE_RR }, - { "", 0, INSTR_INVALID } -}; - -static struct insn opcode_c0[] = { -#ifdef CONFIG_64BIT - { "lgfi", 0x01, INSTR_RIL_RI }, - { "xihf", 0x06, INSTR_RIL_RU }, - { "xilf", 0x07, INSTR_RIL_RU }, - { "iihf", 0x08, INSTR_RIL_RU }, - { "iilf", 0x09, INSTR_RIL_RU }, - { "nihf", 0x0a, INSTR_RIL_RU }, - { "nilf", 0x0b, INSTR_RIL_RU }, - { "oihf", 0x0c, INSTR_RIL_RU }, - { "oilf", 0x0d, INSTR_RIL_RU }, - { "llihf", 0x0e, INSTR_RIL_RU }, - { "llilf", 0x0f, INSTR_RIL_RU }, -#endif - { "larl", 0x00, INSTR_RIL_RP }, - { "brcl", 0x04, INSTR_RIL_UP }, - { "brasl", 0x05, INSTR_RIL_RP }, - { "", 0, INSTR_INVALID } -}; - -static struct insn opcode_c2[] = { -#ifdef CONFIG_64BIT - { "slgfi", 0x04, INSTR_RIL_RU }, - { "slfi", 0x05, INSTR_RIL_RU }, - { "agfi", 0x08, INSTR_RIL_RI }, - { "afi", 0x09, INSTR_RIL_RI }, - { "algfi", 0x0a, INSTR_RIL_RU }, - { "alfi", 0x0b, INSTR_RIL_RU }, - { "cgfi", 0x0c, INSTR_RIL_RI }, - { "cfi", 0x0d, INSTR_RIL_RI }, - { "clgfi", 0x0e, INSTR_RIL_RU }, - { "clfi", 0x0f, INSTR_RIL_RU }, - { "msfi", 0x01, INSTR_RIL_RI }, - { "msgfi", 0x00, INSTR_RIL_RI }, -#endif - { "", 0, INSTR_INVALID } -}; - -static struct insn opcode_c4[] = { -#ifdef CONFIG_64BIT - { "lrl", 0x0d, INSTR_RIL_RP }, - { "lgrl", 0x08, INSTR_RIL_RP }, - { "lgfrl", 0x0c, INSTR_RIL_RP }, - { "lhrl", 0x05, INSTR_RIL_RP }, - { "lghrl", 0x04, INSTR_RIL_RP }, - { { 0, LONG_INSN_LLGFRL }, 0x0e, INSTR_RIL_RP }, - { "llhrl", 0x02, INSTR_RIL_RP }, - { { 0, LONG_INSN_LLGHRL }, 0x06, INSTR_RIL_RP }, - { "strl", 0x0f, INSTR_RIL_RP }, - { "stgrl", 0x0b, INSTR_RIL_RP }, - { "sthrl", 0x07, INSTR_RIL_RP }, -#endif - { "", 0, INSTR_INVALID } -}; - -static struct insn opcode_c6[] = { -#ifdef CONFIG_64BIT - { "crl", 0x0d, INSTR_RIL_RP }, - { "cgrl", 0x08, INSTR_RIL_RP }, - { "cgfrl", 0x0c, INSTR_RIL_RP }, - { "chrl", 0x05, INSTR_RIL_RP }, - { "cghrl", 0x04, INSTR_RIL_RP }, - { "clrl", 0x0f, INSTR_RIL_RP }, - { "clgrl", 0x0a, INSTR_RIL_RP }, - { { 0, LONG_INSN_CLGFRL }, 0x0e, INSTR_RIL_RP }, - { "clhrl", 0x07, INSTR_RIL_RP }, - { { 0, LONG_INSN_CLGHRL }, 0x06, INSTR_RIL_RP }, - { "pfdrl", 0x02, INSTR_RIL_UP }, - { "exrl", 0x00, INSTR_RIL_RP }, -#endif - { "", 0, INSTR_INVALID } -}; - -static struct insn opcode_c8[] = { -#ifdef CONFIG_64BIT - { "mvcos", 0x00, INSTR_SSF_RRDRD }, - { "ectg", 0x01, INSTR_SSF_RRDRD }, - { "csst", 0x02, INSTR_SSF_RRDRD }, - { "lpd", 0x04, INSTR_SSF_RRDRD2 }, - { "lpdg ", 0x05, INSTR_SSF_RRDRD2 }, -#endif - { "", 0, INSTR_INVALID } -}; - -static struct insn opcode_cc[] = { -#ifdef CONFIG_64BIT - { "brcth", 0x06, INSTR_RIL_RP }, - { "aih", 0x08, INSTR_RIL_RI }, - { "alsih", 0x0a, INSTR_RIL_RI }, - { "alsih", 0x0b, INSTR_RIL_RI }, - { "cih", 0x0d, INSTR_RIL_RI }, - { "clih ", 0x0f, INSTR_RIL_RI }, -#endif - { "", 0, INSTR_INVALID } -}; - -static struct insn opcode_e3[] = { -#ifdef CONFIG_64BIT - { "ltg", 0x02, INSTR_RXY_RRRD }, - { "lrag", 0x03, INSTR_RXY_RRRD }, - { "lg", 0x04, INSTR_RXY_RRRD }, - { "cvby", 0x06, INSTR_RXY_RRRD }, - { "ag", 0x08, INSTR_RXY_RRRD }, - { "sg", 0x09, INSTR_RXY_RRRD }, - { "alg", 0x0a, INSTR_RXY_RRRD }, - { "slg", 0x0b, INSTR_RXY_RRRD }, - { "msg", 0x0c, INSTR_RXY_RRRD }, - { "dsg", 0x0d, INSTR_RXY_RRRD }, - { "cvbg", 0x0e, INSTR_RXY_RRRD }, - { "lrvg", 0x0f, INSTR_RXY_RRRD }, - { "lt", 0x12, INSTR_RXY_RRRD }, - { "lray", 0x13, INSTR_RXY_RRRD }, - { "lgf", 0x14, INSTR_RXY_RRRD }, - { "lgh", 0x15, INSTR_RXY_RRRD }, - { "llgf", 0x16, INSTR_RXY_RRRD }, - { "llgt", 0x17, INSTR_RXY_RRRD }, - { "agf", 0x18, INSTR_RXY_RRRD }, - { "sgf", 0x19, INSTR_RXY_RRRD }, - { "algf", 0x1a, INSTR_RXY_RRRD }, - { "slgf", 0x1b, INSTR_RXY_RRRD }, - { "msgf", 0x1c, INSTR_RXY_RRRD }, - { "dsgf", 0x1d, INSTR_RXY_RRRD }, - { "cg", 0x20, INSTR_RXY_RRRD }, - { "clg", 0x21, INSTR_RXY_RRRD }, - { "stg", 0x24, INSTR_RXY_RRRD }, - { "cvdy", 0x26, INSTR_RXY_RRRD }, - { "cvdg", 0x2e, INSTR_RXY_RRRD }, - { "strvg", 0x2f, INSTR_RXY_RRRD }, - { "cgf", 0x30, INSTR_RXY_RRRD }, - { "clgf", 0x31, INSTR_RXY_RRRD }, - { "strvh", 0x3f, INSTR_RXY_RRRD }, - { "bctg", 0x46, INSTR_RXY_RRRD }, - { "sty", 0x50, INSTR_RXY_RRRD }, - { "msy", 0x51, INSTR_RXY_RRRD }, - { "ny", 0x54, INSTR_RXY_RRRD }, - { "cly", 0x55, INSTR_RXY_RRRD }, - { "oy", 0x56, INSTR_RXY_RRRD }, - { "xy", 0x57, INSTR_RXY_RRRD }, - { "ly", 0x58, INSTR_RXY_RRRD }, - { "cy", 0x59, INSTR_RXY_RRRD }, - { "ay", 0x5a, INSTR_RXY_RRRD }, - { "sy", 0x5b, INSTR_RXY_RRRD }, - { "aly", 0x5e, INSTR_RXY_RRRD }, - { "sly", 0x5f, INSTR_RXY_RRRD }, - { "sthy", 0x70, INSTR_RXY_RRRD }, - { "lay", 0x71, INSTR_RXY_RRRD }, - { "stcy", 0x72, INSTR_RXY_RRRD }, - { "icy", 0x73, INSTR_RXY_RRRD }, - { "lb", 0x76, INSTR_RXY_RRRD }, - { "lgb", 0x77, INSTR_RXY_RRRD }, - { "lhy", 0x78, INSTR_RXY_RRRD }, - { "chy", 0x79, INSTR_RXY_RRRD }, - { "ahy", 0x7a, INSTR_RXY_RRRD }, - { "shy", 0x7b, INSTR_RXY_RRRD }, - { "ng", 0x80, INSTR_RXY_RRRD }, - { "og", 0x81, INSTR_RXY_RRRD }, - { "xg", 0x82, INSTR_RXY_RRRD }, - { "mlg", 0x86, INSTR_RXY_RRRD }, - { "dlg", 0x87, INSTR_RXY_RRRD }, - { "alcg", 0x88, INSTR_RXY_RRRD }, - { "slbg", 0x89, INSTR_RXY_RRRD }, - { "stpq", 0x8e, INSTR_RXY_RRRD }, - { "lpq", 0x8f, INSTR_RXY_RRRD }, - { "llgc", 0x90, INSTR_RXY_RRRD }, - { "llgh", 0x91, INSTR_RXY_RRRD }, - { "llc", 0x94, INSTR_RXY_RRRD }, - { "llh", 0x95, INSTR_RXY_RRRD }, - { "cgh", 0x34, INSTR_RXY_RRRD }, - { "laey", 0x75, INSTR_RXY_RRRD }, - { "ltgf", 0x32, INSTR_RXY_RRRD }, - { "mfy", 0x5c, INSTR_RXY_RRRD }, - { "mhy", 0x7c, INSTR_RXY_RRRD }, - { "pfd", 0x36, INSTR_RXY_URRD }, - { "lbh", 0xc0, INSTR_RXY_RRRD }, - { "llch", 0xc2, INSTR_RXY_RRRD }, - { "stch", 0xc3, INSTR_RXY_RRRD }, - { "lhh", 0xc4, INSTR_RXY_RRRD }, - { "llhh", 0xc6, INSTR_RXY_RRRD }, - { "sthh", 0xc7, INSTR_RXY_RRRD }, - { "lfh", 0xca, INSTR_RXY_RRRD }, - { "stfh", 0xcb, INSTR_RXY_RRRD }, - { "chf", 0xcd, INSTR_RXY_RRRD }, - { "clhf", 0xcf, INSTR_RXY_RRRD }, -#endif - { "lrv", 0x1e, INSTR_RXY_RRRD }, - { "lrvh", 0x1f, INSTR_RXY_RRRD }, - { "strv", 0x3e, INSTR_RXY_RRRD }, - { "ml", 0x96, INSTR_RXY_RRRD }, - { "dl", 0x97, INSTR_RXY_RRRD }, - { "alc", 0x98, INSTR_RXY_RRRD }, - { "slb", 0x99, INSTR_RXY_RRRD }, - { "", 0, INSTR_INVALID } -}; - -static struct insn opcode_e5[] = { -#ifdef CONFIG_64BIT - { "strag", 0x02, INSTR_SSE_RDRD }, - { "chhsi", 0x54, INSTR_SIL_RDI }, - { "chsi", 0x5c, INSTR_SIL_RDI }, - { "cghsi", 0x58, INSTR_SIL_RDI }, - { { 0, LONG_INSN_CLHHSI }, 0x55, INSTR_SIL_RDU }, - { { 0, LONG_INSN_CLFHSI }, 0x5d, INSTR_SIL_RDU }, - { { 0, LONG_INSN_CLGHSI }, 0x59, INSTR_SIL_RDU }, - { "mvhhi", 0x44, INSTR_SIL_RDI }, - { "mvhi", 0x4c, INSTR_SIL_RDI }, - { "mvghi", 0x48, INSTR_SIL_RDI }, -#endif - { "lasp", 0x00, INSTR_SSE_RDRD }, - { "tprot", 0x01, INSTR_SSE_RDRD }, - { "mvcsk", 0x0e, INSTR_SSE_RDRD }, - { "mvcdk", 0x0f, INSTR_SSE_RDRD }, - { "", 0, INSTR_INVALID } -}; - -static struct insn opcode_eb[] = { -#ifdef CONFIG_64BIT - { "lmg", 0x04, INSTR_RSY_RRRD }, - { "srag", 0x0a, INSTR_RSY_RRRD }, - { "slag", 0x0b, INSTR_RSY_RRRD }, - { "srlg", 0x0c, INSTR_RSY_RRRD }, - { "sllg", 0x0d, INSTR_RSY_RRRD }, - { "tracg", 0x0f, INSTR_RSY_RRRD }, - { "csy", 0x14, INSTR_RSY_RRRD }, - { "rllg", 0x1c, INSTR_RSY_RRRD }, - { "clmh", 0x20, INSTR_RSY_RURD }, - { "clmy", 0x21, INSTR_RSY_RURD }, - { "stmg", 0x24, INSTR_RSY_RRRD }, - { "stctg", 0x25, INSTR_RSY_CCRD }, - { "stmh", 0x26, INSTR_RSY_RRRD }, - { "stcmh", 0x2c, INSTR_RSY_RURD }, - { "stcmy", 0x2d, INSTR_RSY_RURD }, - { "lctlg", 0x2f, INSTR_RSY_CCRD }, - { "csg", 0x30, INSTR_RSY_RRRD }, - { "cdsy", 0x31, INSTR_RSY_RRRD }, - { "cdsg", 0x3e, INSTR_RSY_RRRD }, - { "bxhg", 0x44, INSTR_RSY_RRRD }, - { "bxleg", 0x45, INSTR_RSY_RRRD }, - { "tmy", 0x51, INSTR_SIY_URD }, - { "mviy", 0x52, INSTR_SIY_URD }, - { "niy", 0x54, INSTR_SIY_URD }, - { "cliy", 0x55, INSTR_SIY_URD }, - { "oiy", 0x56, INSTR_SIY_URD }, - { "xiy", 0x57, INSTR_SIY_URD }, - { "icmh", 0x80, INSTR_RSE_RURD }, - { "icmh", 0x80, INSTR_RSY_RURD }, - { "icmy", 0x81, INSTR_RSY_RURD }, - { "clclu", 0x8f, INSTR_RSY_RRRD }, - { "stmy", 0x90, INSTR_RSY_RRRD }, - { "lmh", 0x96, INSTR_RSY_RRRD }, - { "lmy", 0x98, INSTR_RSY_RRRD }, - { "lamy", 0x9a, INSTR_RSY_AARD }, - { "stamy", 0x9b, INSTR_RSY_AARD }, - { "asi", 0x6a, INSTR_SIY_IRD }, - { "agsi", 0x7a, INSTR_SIY_IRD }, - { "alsi", 0x6e, INSTR_SIY_IRD }, - { "algsi", 0x7e, INSTR_SIY_IRD }, - { "ecag", 0x4c, INSTR_RSY_RRRD }, - { "srak", 0xdc, INSTR_RSY_RRRD }, - { "slak", 0xdd, INSTR_RSY_RRRD }, - { "srlk", 0xde, INSTR_RSY_RRRD }, - { "sllk", 0xdf, INSTR_RSY_RRRD }, - { "locg", 0xe2, INSTR_RSY_RDRM }, - { "stocg", 0xe3, INSTR_RSY_RDRM }, - { "lang", 0xe4, INSTR_RSY_RRRD }, - { "laog", 0xe6, INSTR_RSY_RRRD }, - { "laxg", 0xe7, INSTR_RSY_RRRD }, - { "laag", 0xe8, INSTR_RSY_RRRD }, - { "laalg", 0xea, INSTR_RSY_RRRD }, - { "loc", 0xf2, INSTR_RSY_RDRM }, - { "stoc", 0xf3, INSTR_RSY_RDRM }, - { "lan", 0xf4, INSTR_RSY_RRRD }, - { "lao", 0xf6, INSTR_RSY_RRRD }, - { "lax", 0xf7, INSTR_RSY_RRRD }, - { "laa", 0xf8, INSTR_RSY_RRRD }, - { "laal", 0xfa, INSTR_RSY_RRRD }, -#endif - { "rll", 0x1d, INSTR_RSY_RRRD }, - { "mvclu", 0x8e, INSTR_RSY_RRRD }, - { "tp", 0xc0, INSTR_RSL_R0RD }, - { "", 0, INSTR_INVALID } -}; - -static struct insn opcode_ec[] = { -#ifdef CONFIG_64BIT - { "brxhg", 0x44, INSTR_RIE_RRP }, - { "brxlg", 0x45, INSTR_RIE_RRP }, - { "crb", 0xf6, INSTR_RRS_RRRDU }, - { "cgrb", 0xe4, INSTR_RRS_RRRDU }, - { "crj", 0x76, INSTR_RIE_RRPU }, - { "cgrj", 0x64, INSTR_RIE_RRPU }, - { "cib", 0xfe, INSTR_RIS_RURDI }, - { "cgib", 0xfc, INSTR_RIS_RURDI }, - { "cij", 0x7e, INSTR_RIE_RUPI }, - { "cgij", 0x7c, INSTR_RIE_RUPI }, - { "cit", 0x72, INSTR_RIE_R0IU }, - { "cgit", 0x70, INSTR_RIE_R0IU }, - { "clrb", 0xf7, INSTR_RRS_RRRDU }, - { "clgrb", 0xe5, INSTR_RRS_RRRDU }, - { "clrj", 0x77, INSTR_RIE_RRPU }, - { "clgrj", 0x65, INSTR_RIE_RRPU }, - { "clib", 0xff, INSTR_RIS_RURDU }, - { "clgib", 0xfd, INSTR_RIS_RURDU }, - { "clij", 0x7f, INSTR_RIE_RUPU }, - { "clgij", 0x7d, INSTR_RIE_RUPU }, - { "clfit", 0x73, INSTR_RIE_R0UU }, - { "clgit", 0x71, INSTR_RIE_R0UU }, - { "rnsbg", 0x54, INSTR_RIE_RRUUU }, - { "rxsbg", 0x57, INSTR_RIE_RRUUU }, - { "rosbg", 0x56, INSTR_RIE_RRUUU }, - { "risbg", 0x55, INSTR_RIE_RRUUU }, - { { 0, LONG_INSN_RISBLG }, 0x51, INSTR_RIE_RRUUU }, - { { 0, LONG_INSN_RISBHG }, 0x5D, INSTR_RIE_RRUUU }, - { "ahik", 0xd8, INSTR_RIE_RRI0 }, - { "aghik", 0xd9, INSTR_RIE_RRI0 }, - { { 0, LONG_INSN_ALHSIK }, 0xda, INSTR_RIE_RRI0 }, - { { 0, LONG_INSN_ALGHSIK }, 0xdb, INSTR_RIE_RRI0 }, -#endif - { "", 0, INSTR_INVALID } -}; - -static struct insn opcode_ed[] = { -#ifdef CONFIG_64BIT - { "mayl", 0x38, INSTR_RXF_FRRDF }, - { "myl", 0x39, INSTR_RXF_FRRDF }, - { "may", 0x3a, INSTR_RXF_FRRDF }, - { "my", 0x3b, INSTR_RXF_FRRDF }, - { "mayh", 0x3c, INSTR_RXF_FRRDF }, - { "myh", 0x3d, INSTR_RXF_FRRDF }, - { "ley", 0x64, INSTR_RXY_FRRD }, - { "ldy", 0x65, INSTR_RXY_FRRD }, - { "stey", 0x66, INSTR_RXY_FRRD }, - { "stdy", 0x67, INSTR_RXY_FRRD }, - { "sldt", 0x40, INSTR_RXF_FRRDF }, - { "slxt", 0x48, INSTR_RXF_FRRDF }, - { "srdt", 0x41, INSTR_RXF_FRRDF }, - { "srxt", 0x49, INSTR_RXF_FRRDF }, - { "tdcet", 0x50, INSTR_RXE_FRRD }, - { "tdcdt", 0x54, INSTR_RXE_FRRD }, - { "tdcxt", 0x58, INSTR_RXE_FRRD }, - { "tdget", 0x51, INSTR_RXE_FRRD }, - { "tdgdt", 0x55, INSTR_RXE_FRRD }, - { "tdgxt", 0x59, INSTR_RXE_FRRD }, -#endif - { "ldeb", 0x04, INSTR_RXE_FRRD }, - { "lxdb", 0x05, INSTR_RXE_FRRD }, - { "lxeb", 0x06, INSTR_RXE_FRRD }, - { "mxdb", 0x07, INSTR_RXE_FRRD }, - { "keb", 0x08, INSTR_RXE_FRRD }, - { "ceb", 0x09, INSTR_RXE_FRRD }, - { "aeb", 0x0a, INSTR_RXE_FRRD }, - { "seb", 0x0b, INSTR_RXE_FRRD }, - { "mdeb", 0x0c, INSTR_RXE_FRRD }, - { "deb", 0x0d, INSTR_RXE_FRRD }, - { "maeb", 0x0e, INSTR_RXF_FRRDF }, - { "mseb", 0x0f, INSTR_RXF_FRRDF }, - { "tceb", 0x10, INSTR_RXE_FRRD }, - { "tcdb", 0x11, INSTR_RXE_FRRD }, - { "tcxb", 0x12, INSTR_RXE_FRRD }, - { "sqeb", 0x14, INSTR_RXE_FRRD }, - { "sqdb", 0x15, INSTR_RXE_FRRD }, - { "meeb", 0x17, INSTR_RXE_FRRD }, - { "kdb", 0x18, INSTR_RXE_FRRD }, - { "cdb", 0x19, INSTR_RXE_FRRD }, - { "adb", 0x1a, INSTR_RXE_FRRD }, - { "sdb", 0x1b, INSTR_RXE_FRRD }, - { "mdb", 0x1c, INSTR_RXE_FRRD }, - { "ddb", 0x1d, INSTR_RXE_FRRD }, - { "madb", 0x1e, INSTR_RXF_FRRDF }, - { "msdb", 0x1f, INSTR_RXF_FRRDF }, - { "lde", 0x24, INSTR_RXE_FRRD }, - { "lxd", 0x25, INSTR_RXE_FRRD }, - { "lxe", 0x26, INSTR_RXE_FRRD }, - { "mae", 0x2e, INSTR_RXF_FRRDF }, - { "mse", 0x2f, INSTR_RXF_FRRDF }, - { "sqe", 0x34, INSTR_RXE_FRRD }, - { "sqd", 0x35, INSTR_RXE_FRRD }, - { "mee", 0x37, INSTR_RXE_FRRD }, - { "mad", 0x3e, INSTR_RXF_FRRDF }, - { "msd", 0x3f, INSTR_RXF_FRRDF }, - { "", 0, INSTR_INVALID } -}; - -/* Extracts an operand value from an instruction. */ -static unsigned int extract_operand(unsigned char *code, - const struct operand *operand) -{ - unsigned int val; - int bits; - - /* Extract fragments of the operand byte for byte. */ - code += operand->shift / 8; - bits = (operand->shift & 7) + operand->bits; - val = 0; - do { - val <<= 8; - val |= (unsigned int) *code++; - bits -= 8; - } while (bits > 0); - val >>= -bits; - val &= ((1U << (operand->bits - 1)) << 1) - 1; - - /* Check for special long displacement case. */ - if (operand->bits == 20 && operand->shift == 20) - val = (val & 0xff) << 12 | (val & 0xfff00) >> 8; - - /* Sign extend value if the operand is signed or pc relative. */ - if ((operand->flags & (OPERAND_SIGNED | OPERAND_PCREL)) && - (val & (1U << (operand->bits - 1)))) - val |= (-1U << (operand->bits - 1)) << 1; - - /* Double value if the operand is pc relative. */ - if (operand->flags & OPERAND_PCREL) - val <<= 1; - - /* Length x in an instructions has real length x + 1. */ - if (operand->flags & OPERAND_LENGTH) - val++; - return val; -} - -static inline int insn_length(unsigned char code) -{ - return ((((int) code + 64) >> 7) + 1) << 1; -} - -static struct insn *find_insn(unsigned char *code) -{ - unsigned char opfrag = code[1]; - unsigned char opmask; - struct insn *table; - - switch (code[0]) { - case 0x01: - table = opcode_01; - break; - case 0xa5: - table = opcode_a5; - break; - case 0xa7: - table = opcode_a7; - break; - case 0xb2: - table = opcode_b2; - break; - case 0xb3: - table = opcode_b3; - break; - case 0xb9: - table = opcode_b9; - break; - case 0xc0: - table = opcode_c0; - break; - case 0xc2: - table = opcode_c2; - break; - case 0xc4: - table = opcode_c4; - break; - case 0xc6: - table = opcode_c6; - break; - case 0xc8: - table = opcode_c8; - break; - case 0xcc: - table = opcode_cc; - break; - case 0xe3: - table = opcode_e3; - opfrag = code[5]; - break; - case 0xe5: - table = opcode_e5; - break; - case 0xeb: - table = opcode_eb; - opfrag = code[5]; - break; - case 0xec: - table = opcode_ec; - opfrag = code[5]; - break; - case 0xed: - table = opcode_ed; - opfrag = code[5]; - break; - default: - table = opcode; - opfrag = code[0]; - break; - } - while (table->format != INSTR_INVALID) { - opmask = formats[table->format][0]; - if (table->opfrag == (opfrag & opmask)) - return table; - table++; - } - return NULL; -} - -static int print_insn(char *buffer, unsigned char *code, unsigned long addr) -{ - struct insn *insn; - const unsigned char *ops; - const struct operand *operand; - unsigned int value; - char separator; - char *ptr; - int i; - - ptr = buffer; - insn = find_insn(code); - if (insn) { - if (insn->name[0] == '\0') - ptr += sprintf(ptr, "%s\t", - long_insn_name[(int) insn->name[1]]); - else - ptr += sprintf(ptr, "%.5s\t", insn->name); - /* Extract the operands. */ - separator = 0; - for (ops = formats[insn->format] + 1, i = 0; - *ops != 0 && i < 6; ops++, i++) { - operand = operands + *ops; - value = extract_operand(code, operand); - if ((operand->flags & OPERAND_INDEX) && value == 0) - continue; - if ((operand->flags & OPERAND_BASE) && - value == 0 && separator == '(') { - separator = ','; - continue; - } - if (separator) - ptr += sprintf(ptr, "%c", separator); - if (operand->flags & OPERAND_GPR) - ptr += sprintf(ptr, "%%r%i", value); - else if (operand->flags & OPERAND_FPR) - ptr += sprintf(ptr, "%%f%i", value); - else if (operand->flags & OPERAND_AR) - ptr += sprintf(ptr, "%%a%i", value); - else if (operand->flags & OPERAND_CR) - ptr += sprintf(ptr, "%%c%i", value); - else if (operand->flags & OPERAND_PCREL) - ptr += sprintf(ptr, "%lx", (signed int) value - + addr); - else if (operand->flags & OPERAND_SIGNED) - ptr += sprintf(ptr, "%i", value); - else - ptr += sprintf(ptr, "%u", value); - if (operand->flags & OPERAND_DISP) - separator = '('; - else if (operand->flags & OPERAND_BASE) { - ptr += sprintf(ptr, ")"); - separator = ','; - } else - separator = ','; - } - } else - ptr += sprintf(ptr, "unknown"); - return (int) (ptr - buffer); -} - -void show_code(struct pt_regs *regs) -{ - char *mode = (regs->psw.mask & PSW_MASK_PSTATE) ? "User" : "Krnl"; - unsigned char code[64]; - char buffer[64], *ptr; - mm_segment_t old_fs; - unsigned long addr; - int start, end, opsize, hops, i; - - /* Get a snapshot of the 64 bytes surrounding the fault address. */ - old_fs = get_fs(); - set_fs((regs->psw.mask & PSW_MASK_PSTATE) ? USER_DS : KERNEL_DS); - for (start = 32; start && regs->psw.addr >= 34 - start; start -= 2) { - addr = regs->psw.addr - 34 + start; - if (__copy_from_user(code + start - 2, - (char __user *) addr, 2)) - break; - } - for (end = 32; end < 64; end += 2) { - addr = regs->psw.addr + end - 32; - if (__copy_from_user(code + end, - (char __user *) addr, 2)) - break; - } - set_fs(old_fs); - /* Code snapshot useable ? */ - if ((regs->psw.addr & 1) || start >= end) { - printk("%s Code: Bad PSW.\n", mode); - return; - } - /* Find a starting point for the disassembly. */ - while (start < 32) { - for (i = 0, hops = 0; start + i < 32 && hops < 3; hops++) { - if (!find_insn(code + start + i)) - break; - i += insn_length(code[start + i]); - } - if (start + i == 32) - /* Looks good, sequence ends at PSW. */ - break; - start += 2; - } - /* Decode the instructions. */ - ptr = buffer; - ptr += sprintf(ptr, "%s Code:", mode); - hops = 0; - while (start < end && hops < 8) { - opsize = insn_length(code[start]); - if (start + opsize == 32) - *ptr++ = '#'; - else if (start == 32) - *ptr++ = '>'; - else - *ptr++ = ' '; - addr = regs->psw.addr + start - 32; - ptr += sprintf(ptr, ONELONG, addr); - if (start + opsize >= end) - break; - for (i = 0; i < opsize; i++) - ptr += sprintf(ptr, "%02x", code[start + i]); - *ptr++ = '\t'; - if (i < 6) - *ptr++ = '\t'; - ptr += print_insn(ptr, code + start, addr); - start += opsize; - printk(buffer); - ptr = buffer; - ptr += sprintf(ptr, "\n "); - hops++; - } - printk("\n"); -} diff --git a/ANDROID_3.4.5/arch/s390/kernel/early.c b/ANDROID_3.4.5/arch/s390/kernel/early.c deleted file mode 100644 index 9475e682..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/early.c +++ /dev/null @@ -1,482 +0,0 @@ -/* - * arch/s390/kernel/early.c - * - * Copyright IBM Corp. 2007, 2009 - * Author(s): Hongjie Yang <hongjie@us.ibm.com>, - * Heiko Carstens <heiko.carstens@de.ibm.com> - */ - -#define KMSG_COMPONENT "setup" -#define pr_fmt(fmt) KMSG_COMPONENT ": " fmt - -#include <linux/compiler.h> -#include <linux/init.h> -#include <linux/errno.h> -#include <linux/string.h> -#include <linux/ctype.h> -#include <linux/ftrace.h> -#include <linux/lockdep.h> -#include <linux/module.h> -#include <linux/pfn.h> -#include <linux/uaccess.h> -#include <linux/kernel.h> -#include <asm/ebcdic.h> -#include <asm/ipl.h> -#include <asm/lowcore.h> -#include <asm/processor.h> -#include <asm/sections.h> -#include <asm/setup.h> -#include <asm/sysinfo.h> -#include <asm/cpcmd.h> -#include <asm/sclp.h> -#include <asm/facility.h> -#include "entry.h" - -/* - * Create a Kernel NSS if the SAVESYS= parameter is defined - */ -#define DEFSYS_CMD_SIZE 128 -#define SAVESYS_CMD_SIZE 32 - -char kernel_nss_name[NSS_NAME_SIZE + 1]; - -static void __init setup_boot_command_line(void); - -/* - * Get the TOD clock running. - */ -static void __init reset_tod_clock(void) -{ - u64 time; - - if (store_clock(&time) == 0) - return; - /* TOD clock not running. Set the clock to Unix Epoch. */ - if (set_clock(TOD_UNIX_EPOCH) != 0 || store_clock(&time) != 0) - disabled_wait(0); - - sched_clock_base_cc = TOD_UNIX_EPOCH; - S390_lowcore.last_update_clock = sched_clock_base_cc; -} - -#ifdef CONFIG_SHARED_KERNEL -int __init savesys_ipl_nss(char *cmd, const int cmdlen); - -asm( - " .section .init.text,\"ax\",@progbits\n" - " .align 4\n" - " .type savesys_ipl_nss, @function\n" - "savesys_ipl_nss:\n" -#ifdef CONFIG_64BIT - " stmg 6,15,48(15)\n" - " lgr 14,3\n" - " sam31\n" - " diag 2,14,0x8\n" - " sam64\n" - " lgr 2,14\n" - " lmg 6,15,48(15)\n" -#else - " stm 6,15,24(15)\n" - " lr 14,3\n" - " diag 2,14,0x8\n" - " lr 2,14\n" - " lm 6,15,24(15)\n" -#endif - " br 14\n" - " .size savesys_ipl_nss, .-savesys_ipl_nss\n" - " .previous\n"); - -static __initdata char upper_command_line[COMMAND_LINE_SIZE]; - -static noinline __init void create_kernel_nss(void) -{ - unsigned int i, stext_pfn, eshared_pfn, end_pfn, min_size; -#ifdef CONFIG_BLK_DEV_INITRD - unsigned int sinitrd_pfn, einitrd_pfn; -#endif - int response; - int hlen; - size_t len; - char *savesys_ptr; - char defsys_cmd[DEFSYS_CMD_SIZE]; - char savesys_cmd[SAVESYS_CMD_SIZE]; - - /* Do nothing if we are not running under VM */ - if (!MACHINE_IS_VM) - return; - - /* Convert COMMAND_LINE to upper case */ - for (i = 0; i < strlen(boot_command_line); i++) - upper_command_line[i] = toupper(boot_command_line[i]); - - savesys_ptr = strstr(upper_command_line, "SAVESYS="); - - if (!savesys_ptr) - return; - - savesys_ptr += 8; /* Point to the beginning of the NSS name */ - for (i = 0; i < NSS_NAME_SIZE; i++) { - if (savesys_ptr[i] == ' ' || savesys_ptr[i] == '\0') - break; - kernel_nss_name[i] = savesys_ptr[i]; - } - - stext_pfn = PFN_DOWN(__pa(&_stext)); - eshared_pfn = PFN_DOWN(__pa(&_eshared)); - end_pfn = PFN_UP(__pa(&_end)); - min_size = end_pfn << 2; - - hlen = snprintf(defsys_cmd, DEFSYS_CMD_SIZE, - "DEFSYS %s 00000-%.5X EW %.5X-%.5X SR %.5X-%.5X", - kernel_nss_name, stext_pfn - 1, stext_pfn, - eshared_pfn - 1, eshared_pfn, end_pfn); - -#ifdef CONFIG_BLK_DEV_INITRD - if (INITRD_START && INITRD_SIZE) { - sinitrd_pfn = PFN_DOWN(__pa(INITRD_START)); - einitrd_pfn = PFN_UP(__pa(INITRD_START + INITRD_SIZE)); - min_size = einitrd_pfn << 2; - hlen += snprintf(defsys_cmd + hlen, DEFSYS_CMD_SIZE - hlen, - " EW %.5X-%.5X", sinitrd_pfn, einitrd_pfn); - } -#endif - - snprintf(defsys_cmd + hlen, DEFSYS_CMD_SIZE - hlen, - " EW MINSIZE=%.7iK PARMREGS=0-13", min_size); - defsys_cmd[DEFSYS_CMD_SIZE - 1] = '\0'; - snprintf(savesys_cmd, SAVESYS_CMD_SIZE, "SAVESYS %s \n IPL %s", - kernel_nss_name, kernel_nss_name); - savesys_cmd[SAVESYS_CMD_SIZE - 1] = '\0'; - - __cpcmd(defsys_cmd, NULL, 0, &response); - - if (response != 0) { - pr_err("Defining the Linux kernel NSS failed with rc=%d\n", - response); - kernel_nss_name[0] = '\0'; - return; - } - - len = strlen(savesys_cmd); - ASCEBC(savesys_cmd, len); - response = savesys_ipl_nss(savesys_cmd, len); - - /* On success: response is equal to the command size, - * max SAVESYS_CMD_SIZE - * On error: response contains the numeric portion of cp error message. - * for SAVESYS it will be >= 263 - * for missing privilege class, it will be 1 - */ - if (response > SAVESYS_CMD_SIZE || response == 1) { - pr_err("Saving the Linux kernel NSS failed with rc=%d\n", - response); - kernel_nss_name[0] = '\0'; - return; - } - - /* re-initialize cputime accounting. */ - sched_clock_base_cc = get_clock(); - S390_lowcore.last_update_clock = sched_clock_base_cc; - S390_lowcore.last_update_timer = 0x7fffffffffffffffULL; - S390_lowcore.user_timer = 0; - S390_lowcore.system_timer = 0; - asm volatile("SPT 0(%0)" : : "a" (&S390_lowcore.last_update_timer)); - - /* re-setup boot command line with new ipl vm parms */ - ipl_update_parameters(); - setup_boot_command_line(); - - ipl_flags = IPL_NSS_VALID; -} - -#else /* CONFIG_SHARED_KERNEL */ - -static inline void create_kernel_nss(void) { } - -#endif /* CONFIG_SHARED_KERNEL */ - -/* - * Clear bss memory - */ -static noinline __init void clear_bss_section(void) -{ - memset(__bss_start, 0, __bss_stop - __bss_start); -} - -/* - * Initialize storage key for kernel pages - */ -static noinline __init void init_kernel_storage_key(void) -{ - unsigned long end_pfn, init_pfn; - - end_pfn = PFN_UP(__pa(&_end)); - - for (init_pfn = 0 ; init_pfn < end_pfn; init_pfn++) - page_set_storage_key(init_pfn << PAGE_SHIFT, - PAGE_DEFAULT_KEY, 0); -} - -static __initdata struct sysinfo_3_2_2 vmms __aligned(PAGE_SIZE); - -static noinline __init void detect_machine_type(void) -{ - /* Check current-configuration-level */ - if ((stsi(NULL, 0, 0, 0) >> 28) <= 2) { - S390_lowcore.machine_flags |= MACHINE_FLAG_LPAR; - return; - } - /* Get virtual-machine cpu information. */ - if (stsi(&vmms, 3, 2, 2) == -ENOSYS || !vmms.count) - return; - - /* Running under KVM? If not we assume z/VM */ - if (!memcmp(vmms.vm[0].cpi, "\xd2\xe5\xd4", 3)) - S390_lowcore.machine_flags |= MACHINE_FLAG_KVM; - else - S390_lowcore.machine_flags |= MACHINE_FLAG_VM; -} - -static __init void early_pgm_check_handler(void) -{ - unsigned long addr; - const struct exception_table_entry *fixup; - - addr = S390_lowcore.program_old_psw.addr; - fixup = search_exception_tables(addr & PSW_ADDR_INSN); - if (!fixup) - disabled_wait(0); - S390_lowcore.program_old_psw.addr = fixup->fixup | PSW_ADDR_AMODE; -} - -static noinline __init void setup_lowcore_early(void) -{ - psw_t psw; - - psw.mask = PSW_MASK_BASE | PSW_DEFAULT_KEY | PSW_MASK_EA | PSW_MASK_BA; - psw.addr = PSW_ADDR_AMODE | (unsigned long) s390_base_ext_handler; - S390_lowcore.external_new_psw = psw; - psw.addr = PSW_ADDR_AMODE | (unsigned long) s390_base_pgm_handler; - S390_lowcore.program_new_psw = psw; - s390_base_pgm_handler_fn = early_pgm_check_handler; -} - -static noinline __init void setup_facility_list(void) -{ - stfle(S390_lowcore.stfle_fac_list, - ARRAY_SIZE(S390_lowcore.stfle_fac_list)); -} - -static noinline __init void setup_hpage(void) -{ -#ifndef CONFIG_DEBUG_PAGEALLOC - if (!test_facility(2) || !test_facility(8)) - return; - S390_lowcore.machine_flags |= MACHINE_FLAG_HPAGE; - __ctl_set_bit(0, 23); -#endif -} - -static __init void detect_mvpg(void) -{ -#ifndef CONFIG_64BIT - int rc; - - asm volatile( - " la 0,0\n" - " mvpg %2,%2\n" - "0: la %0,0\n" - "1:\n" - EX_TABLE(0b,1b) - : "=d" (rc) : "0" (-EOPNOTSUPP), "a" (0) : "memory", "cc", "0"); - if (!rc) - S390_lowcore.machine_flags |= MACHINE_FLAG_MVPG; -#endif -} - -static __init void detect_ieee(void) -{ -#ifndef CONFIG_64BIT - int rc, tmp; - - asm volatile( - " efpc %1,0\n" - "0: la %0,0\n" - "1:\n" - EX_TABLE(0b,1b) - : "=d" (rc), "=d" (tmp): "0" (-EOPNOTSUPP) : "cc"); - if (!rc) - S390_lowcore.machine_flags |= MACHINE_FLAG_IEEE; -#endif -} - -static __init void detect_csp(void) -{ -#ifndef CONFIG_64BIT - int rc; - - asm volatile( - " la 0,0\n" - " la 1,0\n" - " la 2,4\n" - " csp 0,2\n" - "0: la %0,0\n" - "1:\n" - EX_TABLE(0b,1b) - : "=d" (rc) : "0" (-EOPNOTSUPP) : "cc", "0", "1", "2"); - if (!rc) - S390_lowcore.machine_flags |= MACHINE_FLAG_CSP; -#endif -} - -static __init void detect_diag9c(void) -{ - unsigned int cpu_address; - int rc; - - cpu_address = stap(); - asm volatile( - " diag %2,0,0x9c\n" - "0: la %0,0\n" - "1:\n" - EX_TABLE(0b,1b) - : "=d" (rc) : "0" (-EOPNOTSUPP), "d" (cpu_address) : "cc"); - if (!rc) - S390_lowcore.machine_flags |= MACHINE_FLAG_DIAG9C; -} - -static __init void detect_diag44(void) -{ -#ifdef CONFIG_64BIT - int rc; - - asm volatile( - " diag 0,0,0x44\n" - "0: la %0,0\n" - "1:\n" - EX_TABLE(0b,1b) - : "=d" (rc) : "0" (-EOPNOTSUPP) : "cc"); - if (!rc) - S390_lowcore.machine_flags |= MACHINE_FLAG_DIAG44; -#endif -} - -static __init void detect_machine_facilities(void) -{ -#ifdef CONFIG_64BIT - if (test_facility(3)) - S390_lowcore.machine_flags |= MACHINE_FLAG_IDTE; - if (test_facility(8)) - S390_lowcore.machine_flags |= MACHINE_FLAG_PFMF; - if (test_facility(11)) - S390_lowcore.machine_flags |= MACHINE_FLAG_TOPOLOGY; - if (test_facility(27)) - S390_lowcore.machine_flags |= MACHINE_FLAG_MVCOS; - if (test_facility(40)) - S390_lowcore.machine_flags |= MACHINE_FLAG_SPP; - if (test_facility(25)) - S390_lowcore.machine_flags |= MACHINE_FLAG_STCKF; -#endif -} - -static __init void rescue_initrd(void) -{ -#ifdef CONFIG_BLK_DEV_INITRD - unsigned long min_initrd_addr = (unsigned long) _end + (4UL << 20); - /* - * Just like in case of IPL from VM reader we make sure there is a - * gap of 4MB between end of kernel and start of initrd. - * That way we can also be sure that saving an NSS will succeed, - * which however only requires different segments. - */ - if (!INITRD_START || !INITRD_SIZE) - return; - if (INITRD_START >= min_initrd_addr) - return; - memmove((void *) min_initrd_addr, (void *) INITRD_START, INITRD_SIZE); - INITRD_START = min_initrd_addr; -#endif -} - -/* Set up boot command line */ -static void __init append_to_cmdline(size_t (*ipl_data)(char *, size_t)) -{ - char *parm, *delim; - size_t rc, len; - - len = strlen(boot_command_line); - - delim = boot_command_line + len; /* '\0' character position */ - parm = boot_command_line + len + 1; /* append right after '\0' */ - - rc = ipl_data(parm, COMMAND_LINE_SIZE - len - 1); - if (rc) { - if (*parm == '=') - memmove(boot_command_line, parm + 1, rc); - else - *delim = ' '; /* replace '\0' with space */ - } -} - -static inline int has_ebcdic_char(const char *str) -{ - int i; - - for (i = 0; str[i]; i++) - if (str[i] & 0x80) - return 1; - return 0; -} - -static void __init setup_boot_command_line(void) -{ - COMMAND_LINE[ARCH_COMMAND_LINE_SIZE - 1] = 0; - /* convert arch command line to ascii if necessary */ - if (has_ebcdic_char(COMMAND_LINE)) - EBCASC(COMMAND_LINE, ARCH_COMMAND_LINE_SIZE); - /* copy arch command line */ - strlcpy(boot_command_line, strstrip(COMMAND_LINE), - ARCH_COMMAND_LINE_SIZE); - - /* append IPL PARM data to the boot command line */ - if (MACHINE_IS_VM) - append_to_cmdline(append_ipl_vmparm); - - append_to_cmdline(append_ipl_scpdata); -} - - -/* - * Save ipl parameters, clear bss memory, initialize storage keys - * and create a kernel NSS at startup if the SAVESYS= parm is defined - */ -void __init startup_init(void) -{ - reset_tod_clock(); - ipl_save_parameters(); - rescue_initrd(); - clear_bss_section(); - init_kernel_storage_key(); - lockdep_init(); - lockdep_off(); - sort_main_extable(); - setup_lowcore_early(); - setup_facility_list(); - detect_machine_type(); - ipl_update_parameters(); - setup_boot_command_line(); - create_kernel_nss(); - detect_mvpg(); - detect_ieee(); - detect_csp(); - detect_diag9c(); - detect_diag44(); - detect_machine_facilities(); - setup_hpage(); - sclp_facilities_detect(); - detect_memory_layout(memory_chunk); -#ifdef CONFIG_DYNAMIC_FTRACE - S390_lowcore.ftrace_func = (unsigned long)ftrace_caller; -#endif - lockdep_on(); -} diff --git a/ANDROID_3.4.5/arch/s390/kernel/ebcdic.c b/ANDROID_3.4.5/arch/s390/kernel/ebcdic.c deleted file mode 100644 index cc0dc609..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/ebcdic.c +++ /dev/null @@ -1,401 +0,0 @@ -/* - * arch/s390/kernel/ebcdic.c - * ECBDIC -> ASCII, ASCII -> ECBDIC, - * upper to lower case (EBCDIC) conversion tables. - * - * S390 version - * Copyright (C) 1999 IBM Deutschland Entwicklung GmbH, IBM Corporation - * Author(s): Martin Schwidefsky <schwidefsky@de.ibm.com> - * Martin Peschke <peschke@fh-brandenburg.de> - */ - -#include <linux/module.h> -#include <asm/types.h> -#include <asm/ebcdic.h> - -/* - * ASCII (IBM PC 437) -> EBCDIC 037 - */ -__u8 _ascebc[256] = -{ - /*00 NUL SOH STX ETX EOT ENQ ACK BEL */ - 0x00, 0x01, 0x02, 0x03, 0x37, 0x2D, 0x2E, 0x2F, - /*08 BS HT LF VT FF CR SO SI */ - /* ->NL */ - 0x16, 0x05, 0x15, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F, - /*10 DLE DC1 DC2 DC3 DC4 NAK SYN ETB */ - 0x10, 0x11, 0x12, 0x13, 0x3C, 0x3D, 0x32, 0x26, - /*18 CAN EM SUB ESC FS GS RS US */ - /* ->IGS ->IRS ->IUS */ - 0x18, 0x19, 0x3F, 0x27, 0x22, 0x1D, 0x1E, 0x1F, - /*20 SP ! " # $ % & ' */ - 0x40, 0x5A, 0x7F, 0x7B, 0x5B, 0x6C, 0x50, 0x7D, - /*28 ( ) * + , - . / */ - 0x4D, 0x5D, 0x5C, 0x4E, 0x6B, 0x60, 0x4B, 0x61, - /*30 0 1 2 3 4 5 6 7 */ - 0xF0, 0xF1, 0xF2, 0xF3, 0xF4, 0xF5, 0xF6, 0xF7, - /*38 8 9 : ; < = > ? */ - 0xF8, 0xF9, 0x7A, 0x5E, 0x4C, 0x7E, 0x6E, 0x6F, - /*40 @ A B C D E F G */ - 0x7C, 0xC1, 0xC2, 0xC3, 0xC4, 0xC5, 0xC6, 0xC7, - /*48 H I J K L M N O */ - 0xC8, 0xC9, 0xD1, 0xD2, 0xD3, 0xD4, 0xD5, 0xD6, - /*50 P Q R S T U V W */ - 0xD7, 0xD8, 0xD9, 0xE2, 0xE3, 0xE4, 0xE5, 0xE6, - /*58 X Y Z [ \ ] ^ _ */ - 0xE7, 0xE8, 0xE9, 0xBA, 0xE0, 0xBB, 0xB0, 0x6D, - /*60 ` a b c d e f g */ - 0x79, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87, - /*68 h i j k l m n o */ - 0x88, 0x89, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, - /*70 p q r s t u v w */ - 0x97, 0x98, 0x99, 0xA2, 0xA3, 0xA4, 0xA5, 0xA6, - /*78 x y z { | } ~ DL */ - 0xA7, 0xA8, 0xA9, 0xC0, 0x4F, 0xD0, 0xA1, 0x07, - /*80*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*88*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*90*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*98*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*A0*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*A8*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*B0*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*B8*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*C0*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*C8*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*D0*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*D8*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*E0 sz */ - 0x3F, 0x59, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*E8*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*F0*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*F8*/ - 0x90, 0x3F, 0x3F, 0x3F, 0x3F, 0xEA, 0x3F, 0xFF -}; - -/* - * EBCDIC 037 -> ASCII (IBM PC 437) - */ -__u8 _ebcasc[256] = -{ - /* 0x00 NUL SOH STX ETX *SEL HT *RNL DEL */ - 0x00, 0x01, 0x02, 0x03, 0x07, 0x09, 0x07, 0x7F, - /* 0x08 -GE -SPS -RPT VT FF CR SO SI */ - 0x07, 0x07, 0x07, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F, - /* 0x10 DLE DC1 DC2 DC3 -RES -NL BS -POC - -ENP ->LF */ - 0x10, 0x11, 0x12, 0x13, 0x07, 0x0A, 0x08, 0x07, - /* 0x18 CAN EM -UBS -CU1 -IFS -IGS -IRS -ITB - -IUS */ - 0x18, 0x19, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, - /* 0x20 -DS -SOS FS -WUS -BYP LF ETB ESC - -INP */ - 0x07, 0x07, 0x1C, 0x07, 0x07, 0x0A, 0x17, 0x1B, - /* 0x28 -SA -SFE -SM -CSP -MFA ENQ ACK BEL - -SW */ - 0x07, 0x07, 0x07, 0x07, 0x07, 0x05, 0x06, 0x07, - /* 0x30 ---- ---- SYN -IR -PP -TRN -NBS EOT */ - 0x07, 0x07, 0x16, 0x07, 0x07, 0x07, 0x07, 0x04, - /* 0x38 -SBS -IT -RFF -CU3 DC4 NAK ---- SUB */ - 0x07, 0x07, 0x07, 0x07, 0x14, 0x15, 0x07, 0x1A, - /* 0x40 SP RSP ä ---- */ - 0x20, 0xFF, 0x83, 0x84, 0x85, 0xA0, 0x07, 0x86, - /* 0x48 . < ( + | */ - 0x87, 0xA4, 0x9B, 0x2E, 0x3C, 0x28, 0x2B, 0x7C, - /* 0x50 & ---- */ - 0x26, 0x82, 0x88, 0x89, 0x8A, 0xA1, 0x8C, 0x07, - /* 0x58 ß ! $ * ) ; */ - 0x8D, 0xE1, 0x21, 0x24, 0x2A, 0x29, 0x3B, 0xAA, - /* 0x60 - / ---- Ä ---- ---- ---- */ - 0x2D, 0x2F, 0x07, 0x8E, 0x07, 0x07, 0x07, 0x8F, - /* 0x68 ---- , % _ > ? */ - 0x80, 0xA5, 0x07, 0x2C, 0x25, 0x5F, 0x3E, 0x3F, - /* 0x70 ---- ---- ---- ---- ---- ---- ---- */ - 0x07, 0x90, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, - /* 0x78 * ` : # @ ' = " */ - 0x70, 0x60, 0x3A, 0x23, 0x40, 0x27, 0x3D, 0x22, - /* 0x80 * a b c d e f g */ - 0x07, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67, - /* 0x88 h i ---- ---- ---- */ - 0x68, 0x69, 0xAE, 0xAF, 0x07, 0x07, 0x07, 0xF1, - /* 0x90 ° j k l m n o p */ - 0xF8, 0x6A, 0x6B, 0x6C, 0x6D, 0x6E, 0x6F, 0x70, - /* 0x98 q r ---- ---- */ - 0x71, 0x72, 0xA6, 0xA7, 0x91, 0x07, 0x92, 0x07, - /* 0xA0 ~ s t u v w x */ - 0xE6, 0x7E, 0x73, 0x74, 0x75, 0x76, 0x77, 0x78, - /* 0xA8 y z ---- ---- ---- ---- */ - 0x79, 0x7A, 0xAD, 0xAB, 0x07, 0x07, 0x07, 0x07, - /* 0xB0 ^ ---- § ---- */ - 0x5E, 0x9C, 0x9D, 0xFA, 0x07, 0x07, 0x07, 0xAC, - /* 0xB8 ---- [ ] ---- ---- ---- ---- */ - 0xAB, 0x07, 0x5B, 0x5D, 0x07, 0x07, 0x07, 0x07, - /* 0xC0 { A B C D E F G */ - 0x7B, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47, - /* 0xC8 H I ---- ö ---- */ - 0x48, 0x49, 0x07, 0x93, 0x94, 0x95, 0xA2, 0x07, - /* 0xD0 } J K L M N O P */ - 0x7D, 0x4A, 0x4B, 0x4C, 0x4D, 0x4E, 0x4F, 0x50, - /* 0xD8 Q R ---- ü */ - 0x51, 0x52, 0x07, 0x96, 0x81, 0x97, 0xA3, 0x98, - /* 0xE0 \ S T U V W X */ - 0x5C, 0xF6, 0x53, 0x54, 0x55, 0x56, 0x57, 0x58, - /* 0xE8 Y Z ---- Ö ---- ---- ---- */ - 0x59, 0x5A, 0xFD, 0x07, 0x99, 0x07, 0x07, 0x07, - /* 0xF0 0 1 2 3 4 5 6 7 */ - 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, - /* 0xF8 8 9 ---- ---- Ü ---- ---- ---- */ - 0x38, 0x39, 0x07, 0x07, 0x9A, 0x07, 0x07, 0x07 -}; - - -/* - * ASCII (IBM PC 437) -> EBCDIC 500 - */ -__u8 _ascebc_500[256] = -{ - /*00 NUL SOH STX ETX EOT ENQ ACK BEL */ - 0x00, 0x01, 0x02, 0x03, 0x37, 0x2D, 0x2E, 0x2F, - /*08 BS HT LF VT FF CR SO SI */ - /* ->NL */ - 0x16, 0x05, 0x15, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F, - /*10 DLE DC1 DC2 DC3 DC4 NAK SYN ETB */ - 0x10, 0x11, 0x12, 0x13, 0x3C, 0x3D, 0x32, 0x26, - /*18 CAN EM SUB ESC FS GS RS US */ - /* ->IGS ->IRS ->IUS */ - 0x18, 0x19, 0x3F, 0x27, 0x22, 0x1D, 0x1E, 0x1F, - /*20 SP ! " # $ % & ' */ - 0x40, 0x4F, 0x7F, 0x7B, 0x5B, 0x6C, 0x50, 0x7D, - /*28 ( ) * + , - . / */ - 0x4D, 0x5D, 0x5C, 0x4E, 0x6B, 0x60, 0x4B, 0x61, - /*30 0 1 2 3 4 5 6 7 */ - 0xF0, 0xF1, 0xF2, 0xF3, 0xF4, 0xF5, 0xF6, 0xF7, - /*38 8 9 : ; < = > ? */ - 0xF8, 0xF9, 0x7A, 0x5E, 0x4C, 0x7E, 0x6E, 0x6F, - /*40 @ A B C D E F G */ - 0x7C, 0xC1, 0xC2, 0xC3, 0xC4, 0xC5, 0xC6, 0xC7, - /*48 H I J K L M N O */ - 0xC8, 0xC9, 0xD1, 0xD2, 0xD3, 0xD4, 0xD5, 0xD6, - /*50 P Q R S T U V W */ - 0xD7, 0xD8, 0xD9, 0xE2, 0xE3, 0xE4, 0xE5, 0xE6, - /*58 X Y Z [ \ ] ^ _ */ - 0xE7, 0xE8, 0xE9, 0x4A, 0xE0, 0x5A, 0x5F, 0x6D, - /*60 ` a b c d e f g */ - 0x79, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87, - /*68 h i j k l m n o */ - 0x88, 0x89, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, - /*70 p q r s t u v w */ - 0x97, 0x98, 0x99, 0xA2, 0xA3, 0xA4, 0xA5, 0xA6, - /*78 x y z { | } ~ DL */ - 0xA7, 0xA8, 0xA9, 0xC0, 0xBB, 0xD0, 0xA1, 0x07, - /*80*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*88*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*90*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*98*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*A0*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*A8*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*B0*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*B8*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*C0*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*C8*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*D0*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*D8*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*E0 sz */ - 0x3F, 0x59, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*E8*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*F0*/ - 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, 0x3F, - /*F8*/ - 0x90, 0x3F, 0x3F, 0x3F, 0x3F, 0xEA, 0x3F, 0xFF -}; - -/* - * EBCDIC 500 -> ASCII (IBM PC 437) - */ -__u8 _ebcasc_500[256] = -{ - /* 0x00 NUL SOH STX ETX *SEL HT *RNL DEL */ - 0x00, 0x01, 0x02, 0x03, 0x07, 0x09, 0x07, 0x7F, - /* 0x08 -GE -SPS -RPT VT FF CR SO SI */ - 0x07, 0x07, 0x07, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F, - /* 0x10 DLE DC1 DC2 DC3 -RES -NL BS -POC - -ENP ->LF */ - 0x10, 0x11, 0x12, 0x13, 0x07, 0x0A, 0x08, 0x07, - /* 0x18 CAN EM -UBS -CU1 -IFS -IGS -IRS -ITB - -IUS */ - 0x18, 0x19, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, - /* 0x20 -DS -SOS FS -WUS -BYP LF ETB ESC - -INP */ - 0x07, 0x07, 0x1C, 0x07, 0x07, 0x0A, 0x17, 0x1B, - /* 0x28 -SA -SFE -SM -CSP -MFA ENQ ACK BEL - -SW */ - 0x07, 0x07, 0x07, 0x07, 0x07, 0x05, 0x06, 0x07, - /* 0x30 ---- ---- SYN -IR -PP -TRN -NBS EOT */ - 0x07, 0x07, 0x16, 0x07, 0x07, 0x07, 0x07, 0x04, - /* 0x38 -SBS -IT -RFF -CU3 DC4 NAK ---- SUB */ - 0x07, 0x07, 0x07, 0x07, 0x14, 0x15, 0x07, 0x1A, - /* 0x40 SP RSP ä ---- */ - 0x20, 0xFF, 0x83, 0x84, 0x85, 0xA0, 0x07, 0x86, - /* 0x48 [ . < ( + ! */ - 0x87, 0xA4, 0x5B, 0x2E, 0x3C, 0x28, 0x2B, 0x21, - /* 0x50 & ---- */ - 0x26, 0x82, 0x88, 0x89, 0x8A, 0xA1, 0x8C, 0x07, - /* 0x58 ß ] $ * ) ; ^ */ - 0x8D, 0xE1, 0x5D, 0x24, 0x2A, 0x29, 0x3B, 0x5E, - /* 0x60 - / ---- Ä ---- ---- ---- */ - 0x2D, 0x2F, 0x07, 0x8E, 0x07, 0x07, 0x07, 0x8F, - /* 0x68 ---- , % _ > ? */ - 0x80, 0xA5, 0x07, 0x2C, 0x25, 0x5F, 0x3E, 0x3F, - /* 0x70 ---- ---- ---- ---- ---- ---- ---- */ - 0x07, 0x90, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, - /* 0x78 * ` : # @ ' = " */ - 0x70, 0x60, 0x3A, 0x23, 0x40, 0x27, 0x3D, 0x22, - /* 0x80 * a b c d e f g */ - 0x07, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67, - /* 0x88 h i ---- ---- ---- */ - 0x68, 0x69, 0xAE, 0xAF, 0x07, 0x07, 0x07, 0xF1, - /* 0x90 ° j k l m n o p */ - 0xF8, 0x6A, 0x6B, 0x6C, 0x6D, 0x6E, 0x6F, 0x70, - /* 0x98 q r ---- ---- */ - 0x71, 0x72, 0xA6, 0xA7, 0x91, 0x07, 0x92, 0x07, - /* 0xA0 ~ s t u v w x */ - 0xE6, 0x7E, 0x73, 0x74, 0x75, 0x76, 0x77, 0x78, - /* 0xA8 y z ---- ---- ---- ---- */ - 0x79, 0x7A, 0xAD, 0xAB, 0x07, 0x07, 0x07, 0x07, - /* 0xB0 ---- § ---- */ - 0x9B, 0x9C, 0x9D, 0xFA, 0x07, 0x07, 0x07, 0xAC, - /* 0xB8 ---- | ---- ---- ---- ---- */ - 0xAB, 0x07, 0xAA, 0x7C, 0x07, 0x07, 0x07, 0x07, - /* 0xC0 { A B C D E F G */ - 0x7B, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47, - /* 0xC8 H I ---- ö ---- */ - 0x48, 0x49, 0x07, 0x93, 0x94, 0x95, 0xA2, 0x07, - /* 0xD0 } J K L M N O P */ - 0x7D, 0x4A, 0x4B, 0x4C, 0x4D, 0x4E, 0x4F, 0x50, - /* 0xD8 Q R ---- ü */ - 0x51, 0x52, 0x07, 0x96, 0x81, 0x97, 0xA3, 0x98, - /* 0xE0 \ S T U V W X */ - 0x5C, 0xF6, 0x53, 0x54, 0x55, 0x56, 0x57, 0x58, - /* 0xE8 Y Z ---- Ö ---- ---- ---- */ - 0x59, 0x5A, 0xFD, 0x07, 0x99, 0x07, 0x07, 0x07, - /* 0xF0 0 1 2 3 4 5 6 7 */ - 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, - /* 0xF8 8 9 ---- ---- Ü ---- ---- ---- */ - 0x38, 0x39, 0x07, 0x07, 0x9A, 0x07, 0x07, 0x07 -}; - - -/* - * EBCDIC 037/500 conversion table: - * from upper to lower case - */ -__u8 _ebc_tolower[256] = -{ - 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, - 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F, - 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, - 0x18, 0x19, 0x1A, 0x1B, 0x1C, 0x1D, 0x1E, 0x1F, - 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, - 0x28, 0x29, 0x2A, 0x2B, 0x2C, 0x2D, 0x2E, 0x2F, - 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, - 0x38, 0x39, 0x3A, 0x3B, 0x3C, 0x3D, 0x3E, 0x3F, - 0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47, - 0x48, 0x49, 0x4A, 0x4B, 0x4C, 0x4D, 0x4E, 0x4F, - 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57, - 0x58, 0x59, 0x5A, 0x5B, 0x5C, 0x5D, 0x5E, 0x5F, - 0x60, 0x61, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47, - 0x48, 0x49, 0x6A, 0x6B, 0x6C, 0x6D, 0x6E, 0x6F, - 0x70, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57, - 0x58, 0x79, 0x7A, 0x7B, 0x7C, 0x7D, 0x7E, 0x7F, - 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87, - 0x88, 0x89, 0x8A, 0x8B, 0x8C, 0x8D, 0x8E, 0x8F, - 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97, - 0x98, 0x99, 0x9A, 0x9B, 0x9C, 0x9D, 0x9C, 0x9F, - 0xA0, 0xA1, 0xA2, 0xA3, 0xA4, 0xA5, 0xA6, 0xA7, - 0xA8, 0xA9, 0xAA, 0xAB, 0x8C, 0x8D, 0x8E, 0xAF, - 0xB0, 0xB1, 0xB2, 0xB3, 0xB4, 0xB5, 0xB6, 0xB7, - 0xB8, 0xB9, 0xBA, 0xBB, 0xBC, 0xBD, 0xBE, 0xBF, - 0xC0, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87, - 0x88, 0x89, 0xCA, 0xCB, 0xCC, 0xCD, 0xCE, 0xCF, - 0xD0, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97, - 0x98, 0x99, 0xDA, 0xDB, 0xDC, 0xDD, 0xDE, 0xDF, - 0xE0, 0xE1, 0xA2, 0xA3, 0xA4, 0xA5, 0xA6, 0xA7, - 0xA8, 0xA9, 0xEA, 0xCB, 0xCC, 0xCD, 0xCE, 0xCF, - 0xF0, 0xF1, 0xF2, 0xF3, 0xF4, 0xF5, 0xF6, 0xF7, - 0xF8, 0xF9, 0xFA, 0xDB, 0xDC, 0xDD, 0xDE, 0xFF -}; - - -/* - * EBCDIC 037/500 conversion table: - * from lower to upper case - */ -__u8 _ebc_toupper[256] = -{ - 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, - 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F, - 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, - 0x18, 0x19, 0x1A, 0x1B, 0x1C, 0x1D, 0x1E, 0x1F, - 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, - 0x28, 0x29, 0x2A, 0x2B, 0x2C, 0x2D, 0x2E, 0x2F, - 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, - 0x38, 0x39, 0x3A, 0x3B, 0x3C, 0x3D, 0x3E, 0x3F, - 0x40, 0x41, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67, - 0x68, 0x69, 0x4A, 0x4B, 0x4C, 0x4D, 0x4E, 0x4F, - 0x50, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77, - 0x78, 0x59, 0x5A, 0x5B, 0x5C, 0x5D, 0x5E, 0x5F, - 0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67, - 0x68, 0x69, 0x6A, 0x6B, 0x6C, 0x6D, 0x6E, 0x6F, - 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77, - 0x78, 0x79, 0x7A, 0x7B, 0x7C, 0x7D, 0x7E, 0x7F, - 0x80, 0xC1, 0xC2, 0xC3, 0xC4, 0xC5, 0xC6, 0xC7, - 0xC8, 0xC9, 0x8A, 0x8B, 0xAC, 0xAD, 0xAE, 0x8F, - 0x90, 0xD1, 0xD2, 0xD3, 0xD4, 0xD5, 0xD6, 0xD7, - 0xD8, 0xD9, 0x9A, 0x9B, 0x9E, 0x9D, 0x9E, 0x9F, - 0xA0, 0xA1, 0xE2, 0xE3, 0xE4, 0xE5, 0xE6, 0xE7, - 0xE8, 0xE9, 0xAA, 0xAB, 0xAC, 0xAD, 0xAE, 0xAF, - 0xB0, 0xB1, 0xB2, 0xB3, 0xB4, 0xB5, 0xB6, 0xB7, - 0xB8, 0xB9, 0xBA, 0xBB, 0xBC, 0xBD, 0xBE, 0xBF, - 0xC0, 0xC1, 0xC2, 0xC3, 0xC4, 0xC5, 0xC6, 0xC7, - 0xC8, 0xC9, 0xCA, 0xEB, 0xEC, 0xED, 0xEE, 0xEF, - 0xD0, 0xD1, 0xD2, 0xD3, 0xD4, 0xD5, 0xD6, 0xD7, - 0xD8, 0xD9, 0xDA, 0xFB, 0xFC, 0xFD, 0xFE, 0xDF, - 0xE0, 0xE1, 0xE2, 0xE3, 0xE4, 0xE5, 0xE6, 0xE7, - 0xE8, 0xE9, 0xEA, 0xEB, 0xEC, 0xED, 0xEE, 0xEF, - 0xF0, 0xF1, 0xF2, 0xF3, 0xF4, 0xF5, 0xF6, 0xF7, - 0xF8, 0xF9, 0xFA, 0xFB, 0xFC, 0xFD, 0xFE, 0xFF -}; - -EXPORT_SYMBOL(_ascebc_500); -EXPORT_SYMBOL(_ebcasc_500); -EXPORT_SYMBOL(_ascebc); -EXPORT_SYMBOL(_ebcasc); -EXPORT_SYMBOL(_ebc_tolower); -EXPORT_SYMBOL(_ebc_toupper); - diff --git a/ANDROID_3.4.5/arch/s390/kernel/entry.S b/ANDROID_3.4.5/arch/s390/kernel/entry.S deleted file mode 100644 index 74ee563f..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/entry.S +++ /dev/null @@ -1,967 +0,0 @@ -/* - * arch/s390/kernel/entry.S - * S390 low-level entry points. - * - * Copyright (C) IBM Corp. 1999,2012 - * Author(s): Martin Schwidefsky (schwidefsky@de.ibm.com), - * Hartmut Penner (hp@de.ibm.com), - * Denis Joseph Barrow (djbarrow@de.ibm.com,barrow_dj@yahoo.com), - * Heiko Carstens <heiko.carstens@de.ibm.com> - */ - -#include <linux/init.h> -#include <linux/linkage.h> -#include <asm/cache.h> -#include <asm/errno.h> -#include <asm/ptrace.h> -#include <asm/thread_info.h> -#include <asm/asm-offsets.h> -#include <asm/unistd.h> -#include <asm/page.h> - -__PT_R0 = __PT_GPRS -__PT_R1 = __PT_GPRS + 4 -__PT_R2 = __PT_GPRS + 8 -__PT_R3 = __PT_GPRS + 12 -__PT_R4 = __PT_GPRS + 16 -__PT_R5 = __PT_GPRS + 20 -__PT_R6 = __PT_GPRS + 24 -__PT_R7 = __PT_GPRS + 28 -__PT_R8 = __PT_GPRS + 32 -__PT_R9 = __PT_GPRS + 36 -__PT_R10 = __PT_GPRS + 40 -__PT_R11 = __PT_GPRS + 44 -__PT_R12 = __PT_GPRS + 48 -__PT_R13 = __PT_GPRS + 524 -__PT_R14 = __PT_GPRS + 56 -__PT_R15 = __PT_GPRS + 60 - -_TIF_WORK_SVC = (_TIF_SIGPENDING | _TIF_NOTIFY_RESUME | _TIF_NEED_RESCHED | \ - _TIF_MCCK_PENDING | _TIF_PER_TRAP ) -_TIF_WORK_INT = (_TIF_SIGPENDING | _TIF_NOTIFY_RESUME | _TIF_NEED_RESCHED | \ - _TIF_MCCK_PENDING) -_TIF_TRACE = (_TIF_SYSCALL_TRACE | _TIF_SYSCALL_AUDIT | _TIF_SECCOMP | \ - _TIF_SYSCALL_TRACEPOINT) - -STACK_SHIFT = PAGE_SHIFT + THREAD_ORDER -STACK_SIZE = 1 << STACK_SHIFT - -#define BASED(name) name-system_call(%r13) - - .macro TRACE_IRQS_ON -#ifdef CONFIG_TRACE_IRQFLAGS - basr %r2,%r0 - l %r1,BASED(.Lhardirqs_on) - basr %r14,%r1 # call trace_hardirqs_on_caller -#endif - .endm - - .macro TRACE_IRQS_OFF -#ifdef CONFIG_TRACE_IRQFLAGS - basr %r2,%r0 - l %r1,BASED(.Lhardirqs_off) - basr %r14,%r1 # call trace_hardirqs_off_caller -#endif - .endm - - .macro LOCKDEP_SYS_EXIT -#ifdef CONFIG_LOCKDEP - tm __PT_PSW+1(%r11),0x01 # returning to user ? - jz .+10 - l %r1,BASED(.Llockdep_sys_exit) - basr %r14,%r1 # call lockdep_sys_exit -#endif - .endm - - .macro CHECK_STACK stacksize,savearea -#ifdef CONFIG_CHECK_STACK - tml %r15,\stacksize - CONFIG_STACK_GUARD - la %r14,\savearea - jz stack_overflow -#endif - .endm - - .macro SWITCH_ASYNC savearea,stack,shift - tmh %r8,0x0001 # interrupting from user ? - jnz 1f - lr %r14,%r9 - sl %r14,BASED(.Lcritical_start) - cl %r14,BASED(.Lcritical_length) - jhe 0f - la %r11,\savearea # inside critical section, do cleanup - bras %r14,cleanup_critical - tmh %r8,0x0001 # retest problem state after cleanup - jnz 1f -0: l %r14,\stack # are we already on the target stack? - slr %r14,%r15 - sra %r14,\shift - jnz 1f - CHECK_STACK 1<<\shift,\savearea - j 2f -1: l %r15,\stack # load target stack -2: ahi %r15,-(STACK_FRAME_OVERHEAD + __PT_SIZE) - la %r11,STACK_FRAME_OVERHEAD(%r15) - .endm - - .macro ADD64 high,low,timer - al \high,\timer - al \low,4+\timer - brc 12,.+8 - ahi \high,1 - .endm - - .macro SUB64 high,low,timer - sl \high,\timer - sl \low,4+\timer - brc 3,.+8 - ahi \high,-1 - .endm - - .macro UPDATE_VTIME high,low,enter_timer - lm \high,\low,__LC_EXIT_TIMER - SUB64 \high,\low,\enter_timer - ADD64 \high,\low,__LC_USER_TIMER - stm \high,\low,__LC_USER_TIMER - lm \high,\low,__LC_LAST_UPDATE_TIMER - SUB64 \high,\low,__LC_EXIT_TIMER - ADD64 \high,\low,__LC_SYSTEM_TIMER - stm \high,\low,__LC_SYSTEM_TIMER - mvc __LC_LAST_UPDATE_TIMER(8),\enter_timer - .endm - - .macro REENABLE_IRQS - st %r8,__LC_RETURN_PSW - ni __LC_RETURN_PSW,0xbf - ssm __LC_RETURN_PSW - .endm - - .section .kprobes.text, "ax" - -/* - * Scheduler resume function, called by switch_to - * gpr2 = (task_struct *) prev - * gpr3 = (task_struct *) next - * Returns: - * gpr2 = prev - */ -ENTRY(__switch_to) - l %r4,__THREAD_info(%r2) # get thread_info of prev - l %r5,__THREAD_info(%r3) # get thread_info of next - tm __TI_flags+3(%r4),_TIF_MCCK_PENDING # machine check pending? - jz 0f - ni __TI_flags+3(%r4),255-_TIF_MCCK_PENDING # clear flag in prev - oi __TI_flags+3(%r5),_TIF_MCCK_PENDING # set it in next -0: stm %r6,%r15,__SF_GPRS(%r15) # store gprs of prev task - st %r15,__THREAD_ksp(%r2) # store kernel stack of prev - l %r15,__THREAD_ksp(%r3) # load kernel stack of next - lctl %c4,%c4,__TASK_pid(%r3) # load pid to control reg. 4 - lm %r6,%r15,__SF_GPRS(%r15) # load gprs of next task - st %r3,__LC_CURRENT # store task struct of next - mvc __LC_CURRENT_PID(4,%r0),__TASK_pid(%r3) # store pid of next - st %r5,__LC_THREAD_INFO # store thread info of next - ahi %r5,STACK_SIZE # end of kernel stack of next - st %r5,__LC_KERNEL_STACK # store end of kernel stack - br %r14 - -__critical_start: -/* - * SVC interrupt handler routine. System calls are synchronous events and - * are executed with interrupts enabled. - */ - -ENTRY(system_call) - stpt __LC_SYNC_ENTER_TIMER -sysc_stm: - stm %r8,%r15,__LC_SAVE_AREA_SYNC - l %r12,__LC_THREAD_INFO - l %r13,__LC_SVC_NEW_PSW+4 -sysc_per: - l %r15,__LC_KERNEL_STACK - ahi %r15,-(STACK_FRAME_OVERHEAD + __PT_SIZE) - la %r11,STACK_FRAME_OVERHEAD(%r15) # pointer to pt_regs -sysc_vtime: - UPDATE_VTIME %r8,%r9,__LC_SYNC_ENTER_TIMER - stm %r0,%r7,__PT_R0(%r11) - mvc __PT_R8(32,%r11),__LC_SAVE_AREA_SYNC - mvc __PT_PSW(8,%r11),__LC_SVC_OLD_PSW - mvc __PT_INT_CODE(4,%r11),__LC_SVC_ILC -sysc_do_svc: - oi __TI_flags+3(%r12),_TIF_SYSCALL - lh %r8,__PT_INT_CODE+2(%r11) - sla %r8,2 # shift and test for svc0 - jnz sysc_nr_ok - # svc 0: system call number in %r1 - cl %r1,BASED(.Lnr_syscalls) - jnl sysc_nr_ok - sth %r1,__PT_INT_CODE+2(%r11) - lr %r8,%r1 - sla %r8,2 -sysc_nr_ok: - l %r10,BASED(.Lsys_call_table) # 31 bit system call table - xc __SF_BACKCHAIN(4,%r15),__SF_BACKCHAIN(%r15) - st %r2,__PT_ORIG_GPR2(%r11) - st %r7,STACK_FRAME_OVERHEAD(%r15) - l %r9,0(%r8,%r10) # get system call addr. - tm __TI_flags+2(%r12),_TIF_TRACE >> 8 - jnz sysc_tracesys - basr %r14,%r9 # call sys_xxxx - st %r2,__PT_R2(%r11) # store return value - -sysc_return: - LOCKDEP_SYS_EXIT -sysc_tif: - tm __PT_PSW+1(%r11),0x01 # returning to user ? - jno sysc_restore - tm __TI_flags+3(%r12),_TIF_WORK_SVC - jnz sysc_work # check for work - ni __TI_flags+3(%r12),255-_TIF_SYSCALL -sysc_restore: - mvc __LC_RETURN_PSW(8),__PT_PSW(%r11) - stpt __LC_EXIT_TIMER - lm %r0,%r15,__PT_R0(%r11) - lpsw __LC_RETURN_PSW -sysc_done: - -# -# One of the work bits is on. Find out which one. -# -sysc_work: - tm __TI_flags+3(%r12),_TIF_MCCK_PENDING - jo sysc_mcck_pending - tm __TI_flags+3(%r12),_TIF_NEED_RESCHED - jo sysc_reschedule - tm __TI_flags+3(%r12),_TIF_SIGPENDING - jo sysc_sigpending - tm __TI_flags+3(%r12),_TIF_NOTIFY_RESUME - jo sysc_notify_resume - tm __TI_flags+3(%r12),_TIF_PER_TRAP - jo sysc_singlestep - j sysc_return # beware of critical section cleanup - -# -# _TIF_NEED_RESCHED is set, call schedule -# -sysc_reschedule: - l %r1,BASED(.Lschedule) - la %r14,BASED(sysc_return) - br %r1 # call schedule - -# -# _TIF_MCCK_PENDING is set, call handler -# -sysc_mcck_pending: - l %r1,BASED(.Lhandle_mcck) - la %r14,BASED(sysc_return) - br %r1 # TIF bit will be cleared by handler - -# -# _TIF_SIGPENDING is set, call do_signal -# -sysc_sigpending: - ni __TI_flags+3(%r12),255-_TIF_PER_TRAP # clear TIF_PER_TRAP - lr %r2,%r11 # pass pointer to pt_regs - l %r1,BASED(.Ldo_signal) - basr %r14,%r1 # call do_signal - tm __TI_flags+3(%r12),_TIF_SYSCALL - jno sysc_return - lm %r2,%r7,__PT_R2(%r11) # load svc arguments - xr %r8,%r8 # svc 0 returns -ENOSYS - clc __PT_INT_CODE+2(2,%r11),BASED(.Lnr_syscalls+2) - jnl sysc_nr_ok # invalid svc number -> do svc 0 - lh %r8,__PT_INT_CODE+2(%r11) # load new svc number - sla %r8,2 - j sysc_nr_ok # restart svc - -# -# _TIF_NOTIFY_RESUME is set, call do_notify_resume -# -sysc_notify_resume: - lr %r2,%r11 # pass pointer to pt_regs - l %r1,BASED(.Ldo_notify_resume) - la %r14,BASED(sysc_return) - br %r1 # call do_notify_resume - -# -# _TIF_PER_TRAP is set, call do_per_trap -# -sysc_singlestep: - ni __TI_flags+3(%r12),255-(_TIF_SYSCALL | _TIF_PER_TRAP) - lr %r2,%r11 # pass pointer to pt_regs - l %r1,BASED(.Ldo_per_trap) - la %r14,BASED(sysc_return) - br %r1 # call do_per_trap - -# -# call tracehook_report_syscall_entry/tracehook_report_syscall_exit before -# and after the system call -# -sysc_tracesys: - l %r1,BASED(.Ltrace_enter) - lr %r2,%r11 # pass pointer to pt_regs - la %r3,0 - xr %r0,%r0 - icm %r0,3,__PT_INT_CODE+2(%r11) - st %r0,__PT_R2(%r11) - basr %r14,%r1 # call do_syscall_trace_enter - cl %r2,BASED(.Lnr_syscalls) - jnl sysc_tracenogo - lr %r8,%r2 - sll %r8,2 - l %r9,0(%r8,%r10) -sysc_tracego: - lm %r3,%r7,__PT_R3(%r11) - st %r7,STACK_FRAME_OVERHEAD(%r15) - l %r2,__PT_ORIG_GPR2(%r11) - basr %r14,%r9 # call sys_xxx - st %r2,__PT_R2(%r11) # store return value -sysc_tracenogo: - tm __TI_flags+2(%r12),_TIF_TRACE >> 8 - jz sysc_return - l %r1,BASED(.Ltrace_exit) - lr %r2,%r11 # pass pointer to pt_regs - la %r14,BASED(sysc_return) - br %r1 # call do_syscall_trace_exit - -# -# a new process exits the kernel with ret_from_fork -# -ENTRY(ret_from_fork) - la %r11,STACK_FRAME_OVERHEAD(%r15) - l %r12,__LC_THREAD_INFO - l %r13,__LC_SVC_NEW_PSW+4 - tm __PT_PSW+1(%r11),0x01 # forking a kernel thread ? - jo 0f - st %r15,__PT_R15(%r11) # store stack pointer for new kthread -0: l %r1,BASED(.Lschedule_tail) - basr %r14,%r1 # call schedule_tail - TRACE_IRQS_ON - ssm __LC_SVC_NEW_PSW # reenable interrupts - j sysc_tracenogo - -# -# kernel_execve function needs to deal with pt_regs that is not -# at the usual place -# -ENTRY(kernel_execve) - stm %r12,%r15,48(%r15) - lr %r14,%r15 - l %r13,__LC_SVC_NEW_PSW+4 - ahi %r15,-(STACK_FRAME_OVERHEAD + __PT_SIZE) - st %r14,__SF_BACKCHAIN(%r15) - la %r12,STACK_FRAME_OVERHEAD(%r15) - xc 0(__PT_SIZE,%r12),0(%r12) - l %r1,BASED(.Ldo_execve) - lr %r5,%r12 - basr %r14,%r1 # call do_execve - ltr %r2,%r2 - je 0f - ahi %r15,(STACK_FRAME_OVERHEAD + __PT_SIZE) - lm %r12,%r15,48(%r15) - br %r14 - # execve succeeded. -0: ssm __LC_PGM_NEW_PSW # disable I/O and ext. interrupts - l %r15,__LC_KERNEL_STACK # load ksp - ahi %r15,-(STACK_FRAME_OVERHEAD + __PT_SIZE) - la %r11,STACK_FRAME_OVERHEAD(%r15) - mvc 0(__PT_SIZE,%r11),0(%r12) # copy pt_regs - l %r12,__LC_THREAD_INFO - xc __SF_BACKCHAIN(4,%r15),__SF_BACKCHAIN(%r15) - ssm __LC_SVC_NEW_PSW # reenable interrupts - l %r1,BASED(.Lexecve_tail) - basr %r14,%r1 # call execve_tail - j sysc_return - -/* - * Program check handler routine - */ - -ENTRY(pgm_check_handler) - stpt __LC_SYNC_ENTER_TIMER - stm %r8,%r15,__LC_SAVE_AREA_SYNC - l %r12,__LC_THREAD_INFO - l %r13,__LC_SVC_NEW_PSW+4 - lm %r8,%r9,__LC_PGM_OLD_PSW - tmh %r8,0x0001 # test problem state bit - jnz 1f # -> fault in user space - tmh %r8,0x4000 # PER bit set in old PSW ? - jnz 0f # -> enabled, can't be a double fault - tm __LC_PGM_ILC+3,0x80 # check for per exception - jnz pgm_svcper # -> single stepped svc -0: CHECK_STACK STACK_SIZE,__LC_SAVE_AREA_SYNC - j 2f -1: UPDATE_VTIME %r14,%r15,__LC_SYNC_ENTER_TIMER - l %r15,__LC_KERNEL_STACK -2: ahi %r15,-(STACK_FRAME_OVERHEAD + __PT_SIZE) - la %r11,STACK_FRAME_OVERHEAD(%r15) - stm %r0,%r7,__PT_R0(%r11) - mvc __PT_R8(32,%r11),__LC_SAVE_AREA_SYNC - stm %r8,%r9,__PT_PSW(%r11) - mvc __PT_INT_CODE(4,%r11),__LC_PGM_ILC - mvc __PT_INT_PARM_LONG(4,%r11),__LC_TRANS_EXC_CODE - tm __LC_PGM_ILC+3,0x80 # check for per exception - jz 0f - l %r1,__TI_task(%r12) - tmh %r8,0x0001 # kernel per event ? - jz pgm_kprobe - oi __TI_flags+3(%r12),_TIF_PER_TRAP - mvc __THREAD_per_address(4,%r1),__LC_PER_ADDRESS - mvc __THREAD_per_cause(2,%r1),__LC_PER_CAUSE - mvc __THREAD_per_paid(1,%r1),__LC_PER_PAID -0: REENABLE_IRQS - xc __SF_BACKCHAIN(4,%r15),__SF_BACKCHAIN(%r15) - l %r1,BASED(.Ljump_table) - la %r10,0x7f - n %r10,__PT_INT_CODE(%r11) - je sysc_return - sll %r10,2 - l %r1,0(%r10,%r1) # load address of handler routine - lr %r2,%r11 # pass pointer to pt_regs - basr %r14,%r1 # branch to interrupt-handler - j sysc_return - -# -# PER event in supervisor state, must be kprobes -# -pgm_kprobe: - REENABLE_IRQS - xc __SF_BACKCHAIN(4,%r15),__SF_BACKCHAIN(%r15) - l %r1,BASED(.Ldo_per_trap) - lr %r2,%r11 # pass pointer to pt_regs - basr %r14,%r1 # call do_per_trap - j sysc_return - -# -# single stepped system call -# -pgm_svcper: - oi __TI_flags+3(%r12),_TIF_PER_TRAP - mvc __LC_RETURN_PSW(4),__LC_SVC_NEW_PSW - mvc __LC_RETURN_PSW+4(4),BASED(.Lsysc_per) - lpsw __LC_RETURN_PSW # branch to sysc_per and enable irqs - -/* - * IO interrupt handler routine - */ - -ENTRY(io_int_handler) - stck __LC_INT_CLOCK - stpt __LC_ASYNC_ENTER_TIMER - stm %r8,%r15,__LC_SAVE_AREA_ASYNC - l %r12,__LC_THREAD_INFO - l %r13,__LC_SVC_NEW_PSW+4 - lm %r8,%r9,__LC_IO_OLD_PSW - tmh %r8,0x0001 # interrupting from user ? - jz io_skip - UPDATE_VTIME %r14,%r15,__LC_ASYNC_ENTER_TIMER -io_skip: - SWITCH_ASYNC __LC_SAVE_AREA_ASYNC,__LC_ASYNC_STACK,STACK_SHIFT - stm %r0,%r7,__PT_R0(%r11) - mvc __PT_R8(32,%r11),__LC_SAVE_AREA_ASYNC - stm %r8,%r9,__PT_PSW(%r11) - TRACE_IRQS_OFF - xc __SF_BACKCHAIN(4,%r15),__SF_BACKCHAIN(%r15) - l %r1,BASED(.Ldo_IRQ) - lr %r2,%r11 # pass pointer to pt_regs - basr %r14,%r1 # call do_IRQ -io_return: - LOCKDEP_SYS_EXIT - TRACE_IRQS_ON -io_tif: - tm __TI_flags+3(%r12),_TIF_WORK_INT - jnz io_work # there is work to do (signals etc.) -io_restore: - mvc __LC_RETURN_PSW(8),__PT_PSW(%r11) - stpt __LC_EXIT_TIMER - lm %r0,%r15,__PT_R0(%r11) - lpsw __LC_RETURN_PSW -io_done: - -# -# There is work todo, find out in which context we have been interrupted: -# 1) if we return to user space we can do all _TIF_WORK_INT work -# 2) if we return to kernel code and preemptive scheduling is enabled check -# the preemption counter and if it is zero call preempt_schedule_irq -# Before any work can be done, a switch to the kernel stack is required. -# -io_work: - tm __PT_PSW+1(%r11),0x01 # returning to user ? - jo io_work_user # yes -> do resched & signal -#ifdef CONFIG_PREEMPT - # check for preemptive scheduling - icm %r0,15,__TI_precount(%r12) - jnz io_restore # preemption disabled - tm __TI_flags+3(%r12),_TIF_NEED_RESCHED - jno io_restore - # switch to kernel stack - l %r1,__PT_R15(%r11) - ahi %r1,-(STACK_FRAME_OVERHEAD + __PT_SIZE) - mvc STACK_FRAME_OVERHEAD(__PT_SIZE,%r1),0(%r11) - xc __SF_BACKCHAIN(4,%r1),__SF_BACKCHAIN(%r1) - la %r11,STACK_FRAME_OVERHEAD(%r1) - lr %r15,%r1 - # TRACE_IRQS_ON already done at io_return, call - # TRACE_IRQS_OFF to keep things symmetrical - TRACE_IRQS_OFF - l %r1,BASED(.Lpreempt_irq) - basr %r14,%r1 # call preempt_schedule_irq - j io_return -#else - j io_restore -#endif - -# -# Need to do work before returning to userspace, switch to kernel stack -# -io_work_user: - l %r1,__LC_KERNEL_STACK - ahi %r1,-(STACK_FRAME_OVERHEAD + __PT_SIZE) - mvc STACK_FRAME_OVERHEAD(__PT_SIZE,%r1),0(%r11) - xc __SF_BACKCHAIN(4,%r1),__SF_BACKCHAIN(%r1) - la %r11,STACK_FRAME_OVERHEAD(%r1) - lr %r15,%r1 - -# -# One of the work bits is on. Find out which one. -# Checked are: _TIF_SIGPENDING, _TIF_NOTIFY_RESUME, _TIF_NEED_RESCHED -# and _TIF_MCCK_PENDING -# -io_work_tif: - tm __TI_flags+3(%r12),_TIF_MCCK_PENDING - jo io_mcck_pending - tm __TI_flags+3(%r12),_TIF_NEED_RESCHED - jo io_reschedule - tm __TI_flags+3(%r12),_TIF_SIGPENDING - jo io_sigpending - tm __TI_flags+3(%r12),_TIF_NOTIFY_RESUME - jo io_notify_resume - j io_return # beware of critical section cleanup - -# -# _TIF_MCCK_PENDING is set, call handler -# -io_mcck_pending: - # TRACE_IRQS_ON already done at io_return - l %r1,BASED(.Lhandle_mcck) - basr %r14,%r1 # TIF bit will be cleared by handler - TRACE_IRQS_OFF - j io_return - -# -# _TIF_NEED_RESCHED is set, call schedule -# -io_reschedule: - # TRACE_IRQS_ON already done at io_return - l %r1,BASED(.Lschedule) - ssm __LC_SVC_NEW_PSW # reenable interrupts - basr %r14,%r1 # call scheduler - ssm __LC_PGM_NEW_PSW # disable I/O and ext. interrupts - TRACE_IRQS_OFF - j io_return - -# -# _TIF_SIGPENDING is set, call do_signal -# -io_sigpending: - # TRACE_IRQS_ON already done at io_return - l %r1,BASED(.Ldo_signal) - ssm __LC_SVC_NEW_PSW # reenable interrupts - lr %r2,%r11 # pass pointer to pt_regs - basr %r14,%r1 # call do_signal - ssm __LC_PGM_NEW_PSW # disable I/O and ext. interrupts - TRACE_IRQS_OFF - j io_return - -# -# _TIF_SIGPENDING is set, call do_signal -# -io_notify_resume: - # TRACE_IRQS_ON already done at io_return - l %r1,BASED(.Ldo_notify_resume) - ssm __LC_SVC_NEW_PSW # reenable interrupts - lr %r2,%r11 # pass pointer to pt_regs - basr %r14,%r1 # call do_notify_resume - ssm __LC_PGM_NEW_PSW # disable I/O and ext. interrupts - TRACE_IRQS_OFF - j io_return - -/* - * External interrupt handler routine - */ - -ENTRY(ext_int_handler) - stck __LC_INT_CLOCK - stpt __LC_ASYNC_ENTER_TIMER - stm %r8,%r15,__LC_SAVE_AREA_ASYNC - l %r12,__LC_THREAD_INFO - l %r13,__LC_SVC_NEW_PSW+4 - lm %r8,%r9,__LC_EXT_OLD_PSW - tmh %r8,0x0001 # interrupting from user ? - jz ext_skip - UPDATE_VTIME %r14,%r15,__LC_ASYNC_ENTER_TIMER -ext_skip: - SWITCH_ASYNC __LC_SAVE_AREA_ASYNC,__LC_ASYNC_STACK,STACK_SHIFT - stm %r0,%r7,__PT_R0(%r11) - mvc __PT_R8(32,%r11),__LC_SAVE_AREA_ASYNC - stm %r8,%r9,__PT_PSW(%r11) - TRACE_IRQS_OFF - lr %r2,%r11 # pass pointer to pt_regs - l %r3,__LC_EXT_CPU_ADDR # get cpu address + interruption code - l %r4,__LC_EXT_PARAMS # get external parameters - l %r1,BASED(.Ldo_extint) - basr %r14,%r1 # call do_extint - j io_return - -/* - * Load idle PSW. The second "half" of this function is in cleanup_idle. - */ -ENTRY(psw_idle) - st %r4,__SF_EMPTY(%r15) - basr %r1,0 - la %r1,psw_idle_lpsw+4-.(%r1) - st %r1,__SF_EMPTY+4(%r15) - oi __SF_EMPTY+4(%r15),0x80 - la %r1,.Lvtimer_max-psw_idle_lpsw-4(%r1) - stck __IDLE_ENTER(%r2) - ltr %r5,%r5 - stpt __VQ_IDLE_ENTER(%r3) - jz psw_idle_lpsw - spt 0(%r1) -psw_idle_lpsw: - lpsw __SF_EMPTY(%r15) - br %r14 -psw_idle_end: - -__critical_end: - -/* - * Machine check handler routines - */ - -ENTRY(mcck_int_handler) - stck __LC_MCCK_CLOCK - spt __LC_CPU_TIMER_SAVE_AREA # revalidate cpu timer - lm %r0,%r15,__LC_GPREGS_SAVE_AREA # revalidate gprs - l %r12,__LC_THREAD_INFO - l %r13,__LC_SVC_NEW_PSW+4 - lm %r8,%r9,__LC_MCK_OLD_PSW - tm __LC_MCCK_CODE,0x80 # system damage? - jo mcck_panic # yes -> rest of mcck code invalid - la %r14,__LC_CPU_TIMER_SAVE_AREA - mvc __LC_MCCK_ENTER_TIMER(8),0(%r14) - tm __LC_MCCK_CODE+5,0x02 # stored cpu timer value valid? - jo 3f - la %r14,__LC_SYNC_ENTER_TIMER - clc 0(8,%r14),__LC_ASYNC_ENTER_TIMER - jl 0f - la %r14,__LC_ASYNC_ENTER_TIMER -0: clc 0(8,%r14),__LC_EXIT_TIMER - jl 1f - la %r14,__LC_EXIT_TIMER -1: clc 0(8,%r14),__LC_LAST_UPDATE_TIMER - jl 2f - la %r14,__LC_LAST_UPDATE_TIMER -2: spt 0(%r14) - mvc __LC_MCCK_ENTER_TIMER(8),0(%r14) -3: tm __LC_MCCK_CODE+2,0x09 # mwp + ia of old psw valid? - jno mcck_panic # no -> skip cleanup critical - tm %r8,0x0001 # interrupting from user ? - jz mcck_skip - UPDATE_VTIME %r14,%r15,__LC_MCCK_ENTER_TIMER -mcck_skip: - SWITCH_ASYNC __LC_GPREGS_SAVE_AREA+32,__LC_PANIC_STACK,PAGE_SHIFT - mvc __PT_R0(64,%r11),__LC_GPREGS_SAVE_AREA - stm %r8,%r9,__PT_PSW(%r11) - xc __SF_BACKCHAIN(4,%r15),__SF_BACKCHAIN(%r15) - l %r1,BASED(.Ldo_machine_check) - lr %r2,%r11 # pass pointer to pt_regs - basr %r14,%r1 # call s390_do_machine_check - tm __PT_PSW+1(%r11),0x01 # returning to user ? - jno mcck_return - l %r1,__LC_KERNEL_STACK # switch to kernel stack - ahi %r1,-(STACK_FRAME_OVERHEAD + __PT_SIZE) - mvc STACK_FRAME_OVERHEAD(__PT_SIZE,%r1),0(%r11) - xc __SF_BACKCHAIN(4,%r1),__SF_BACKCHAIN(%r1) - la %r11,STACK_FRAME_OVERHEAD(%r15) - lr %r15,%r1 - ssm __LC_PGM_NEW_PSW # turn dat on, keep irqs off - tm __TI_flags+3(%r12),_TIF_MCCK_PENDING - jno mcck_return - TRACE_IRQS_OFF - l %r1,BASED(.Lhandle_mcck) - basr %r14,%r1 # call s390_handle_mcck - TRACE_IRQS_ON -mcck_return: - mvc __LC_RETURN_MCCK_PSW(8),__PT_PSW(%r11) # move return PSW - tm __LC_RETURN_MCCK_PSW+1,0x01 # returning to user ? - jno 0f - lm %r0,%r15,__PT_R0(%r11) - stpt __LC_EXIT_TIMER - lpsw __LC_RETURN_MCCK_PSW -0: lm %r0,%r15,__PT_R0(%r11) - lpsw __LC_RETURN_MCCK_PSW - -mcck_panic: - l %r14,__LC_PANIC_STACK - slr %r14,%r15 - sra %r14,PAGE_SHIFT - jz 0f - l %r15,__LC_PANIC_STACK -0: ahi %r15,-(STACK_FRAME_OVERHEAD + __PT_SIZE) - j mcck_skip - -# -# PSW restart interrupt handler -# -ENTRY(restart_int_handler) - st %r15,__LC_SAVE_AREA_RESTART - l %r15,__LC_RESTART_STACK - ahi %r15,-__PT_SIZE # create pt_regs on stack - xc 0(__PT_SIZE,%r15),0(%r15) - stm %r0,%r14,__PT_R0(%r15) - mvc __PT_R15(4,%r15),__LC_SAVE_AREA_RESTART - mvc __PT_PSW(8,%r15),__LC_RST_OLD_PSW # store restart old psw - ahi %r15,-STACK_FRAME_OVERHEAD # create stack frame on stack - xc 0(STACK_FRAME_OVERHEAD,%r15),0(%r15) - lm %r1,%r3,__LC_RESTART_FN # load fn, parm & source cpu - ltr %r3,%r3 # test source cpu address - jm 1f # negative -> skip source stop -0: sigp %r4,%r3,1 # sigp sense to source cpu - brc 10,0b # wait for status stored -1: basr %r14,%r1 # call function - stap __SF_EMPTY(%r15) # store cpu address - lh %r3,__SF_EMPTY(%r15) -2: sigp %r4,%r3,5 # sigp stop to current cpu - brc 2,2b -3: j 3b - - .section .kprobes.text, "ax" - -#ifdef CONFIG_CHECK_STACK -/* - * The synchronous or the asynchronous stack overflowed. We are dead. - * No need to properly save the registers, we are going to panic anyway. - * Setup a pt_regs so that show_trace can provide a good call trace. - */ -stack_overflow: - l %r15,__LC_PANIC_STACK # change to panic stack - ahi %r15,-__PT_SIZE # create pt_regs - stm %r0,%r7,__PT_R0(%r15) - stm %r8,%r9,__PT_PSW(%r15) - mvc __PT_R8(32,%r11),0(%r14) - lr %r15,%r11 - ahi %r15,-STACK_FRAME_OVERHEAD - l %r1,BASED(1f) - xc __SF_BACKCHAIN(4,%r15),__SF_BACKCHAIN(%r15) - lr %r2,%r11 # pass pointer to pt_regs - br %r1 # branch to kernel_stack_overflow -1: .long kernel_stack_overflow -#endif - -cleanup_table: - .long system_call + 0x80000000 - .long sysc_do_svc + 0x80000000 - .long sysc_tif + 0x80000000 - .long sysc_restore + 0x80000000 - .long sysc_done + 0x80000000 - .long io_tif + 0x80000000 - .long io_restore + 0x80000000 - .long io_done + 0x80000000 - .long psw_idle + 0x80000000 - .long psw_idle_end + 0x80000000 - -cleanup_critical: - cl %r9,BASED(cleanup_table) # system_call - jl 0f - cl %r9,BASED(cleanup_table+4) # sysc_do_svc - jl cleanup_system_call - cl %r9,BASED(cleanup_table+8) # sysc_tif - jl 0f - cl %r9,BASED(cleanup_table+12) # sysc_restore - jl cleanup_sysc_tif - cl %r9,BASED(cleanup_table+16) # sysc_done - jl cleanup_sysc_restore - cl %r9,BASED(cleanup_table+20) # io_tif - jl 0f - cl %r9,BASED(cleanup_table+24) # io_restore - jl cleanup_io_tif - cl %r9,BASED(cleanup_table+28) # io_done - jl cleanup_io_restore - cl %r9,BASED(cleanup_table+32) # psw_idle - jl 0f - cl %r9,BASED(cleanup_table+36) # psw_idle_end - jl cleanup_idle -0: br %r14 - -cleanup_system_call: - # check if stpt has been executed - cl %r9,BASED(cleanup_system_call_insn) - jh 0f - mvc __LC_SYNC_ENTER_TIMER(8),__LC_ASYNC_ENTER_TIMER - chi %r11,__LC_SAVE_AREA_ASYNC - je 0f - mvc __LC_SYNC_ENTER_TIMER(8),__LC_MCCK_ENTER_TIMER -0: # check if stm has been executed - cl %r9,BASED(cleanup_system_call_insn+4) - jh 0f - mvc __LC_SAVE_AREA_SYNC(32),0(%r11) -0: # set up saved registers r12, and r13 - st %r12,16(%r11) # r12 thread-info pointer - st %r13,20(%r11) # r13 literal-pool pointer - # check if the user time calculation has been done - cl %r9,BASED(cleanup_system_call_insn+8) - jh 0f - l %r10,__LC_EXIT_TIMER - l %r15,__LC_EXIT_TIMER+4 - SUB64 %r10,%r15,__LC_SYNC_ENTER_TIMER - ADD64 %r10,%r15,__LC_USER_TIMER - st %r10,__LC_USER_TIMER - st %r15,__LC_USER_TIMER+4 -0: # check if the system time calculation has been done - cl %r9,BASED(cleanup_system_call_insn+12) - jh 0f - l %r10,__LC_LAST_UPDATE_TIMER - l %r15,__LC_LAST_UPDATE_TIMER+4 - SUB64 %r10,%r15,__LC_EXIT_TIMER - ADD64 %r10,%r15,__LC_SYSTEM_TIMER - st %r10,__LC_SYSTEM_TIMER - st %r15,__LC_SYSTEM_TIMER+4 -0: # update accounting time stamp - mvc __LC_LAST_UPDATE_TIMER(8),__LC_SYNC_ENTER_TIMER - # set up saved register 11 - l %r15,__LC_KERNEL_STACK - ahi %r15,-__PT_SIZE - st %r15,12(%r11) # r11 pt_regs pointer - # fill pt_regs - mvc __PT_R8(32,%r15),__LC_SAVE_AREA_SYNC - stm %r0,%r7,__PT_R0(%r15) - mvc __PT_PSW(8,%r15),__LC_SVC_OLD_PSW - mvc __PT_INT_CODE(4,%r15),__LC_SVC_ILC - # setup saved register 15 - ahi %r15,-STACK_FRAME_OVERHEAD - st %r15,28(%r11) # r15 stack pointer - # set new psw address and exit - l %r9,BASED(cleanup_table+4) # sysc_do_svc + 0x80000000 - br %r14 -cleanup_system_call_insn: - .long system_call + 0x80000000 - .long sysc_stm + 0x80000000 - .long sysc_vtime + 0x80000000 + 36 - .long sysc_vtime + 0x80000000 + 76 - -cleanup_sysc_tif: - l %r9,BASED(cleanup_table+8) # sysc_tif + 0x80000000 - br %r14 - -cleanup_sysc_restore: - cl %r9,BASED(cleanup_sysc_restore_insn) - jhe 0f - l %r9,12(%r11) # get saved pointer to pt_regs - mvc __LC_RETURN_PSW(8),__PT_PSW(%r9) - mvc 0(32,%r11),__PT_R8(%r9) - lm %r0,%r7,__PT_R0(%r9) -0: lm %r8,%r9,__LC_RETURN_PSW - br %r14 -cleanup_sysc_restore_insn: - .long sysc_done - 4 + 0x80000000 - -cleanup_io_tif: - l %r9,BASED(cleanup_table+20) # io_tif + 0x80000000 - br %r14 - -cleanup_io_restore: - cl %r9,BASED(cleanup_io_restore_insn) - jhe 0f - l %r9,12(%r11) # get saved r11 pointer to pt_regs - mvc __LC_RETURN_PSW(8),__PT_PSW(%r9) - mvc 0(32,%r11),__PT_R8(%r9) - lm %r0,%r7,__PT_R0(%r9) -0: lm %r8,%r9,__LC_RETURN_PSW - br %r14 -cleanup_io_restore_insn: - .long io_done - 4 + 0x80000000 - -cleanup_idle: - # copy interrupt clock & cpu timer - mvc __IDLE_EXIT(8,%r2),__LC_INT_CLOCK - mvc __VQ_IDLE_EXIT(8,%r3),__LC_ASYNC_ENTER_TIMER - chi %r11,__LC_SAVE_AREA_ASYNC - je 0f - mvc __IDLE_EXIT(8,%r2),__LC_MCCK_CLOCK - mvc __VQ_IDLE_EXIT(8,%r3),__LC_MCCK_ENTER_TIMER -0: # check if stck has been executed - cl %r9,BASED(cleanup_idle_insn) - jhe 1f - mvc __IDLE_ENTER(8,%r2),__IDLE_EXIT(%r2) - mvc __VQ_IDLE_ENTER(8,%r3),__VQ_IDLE_EXIT(%r3) - j 2f -1: # check if the cpu timer has been reprogrammed - ltr %r5,%r5 - jz 2f - spt __VQ_IDLE_ENTER(%r3) -2: # account system time going idle - lm %r9,%r10,__LC_STEAL_TIMER - ADD64 %r9,%r10,__IDLE_ENTER(%r2) - SUB64 %r9,%r10,__LC_LAST_UPDATE_CLOCK - stm %r9,%r10,__LC_STEAL_TIMER - mvc __LC_LAST_UPDATE_CLOCK(8),__IDLE_EXIT(%r2) - lm %r9,%r10,__LC_SYSTEM_TIMER - ADD64 %r9,%r10,__LC_LAST_UPDATE_TIMER - SUB64 %r9,%r10,__VQ_IDLE_ENTER(%r3) - stm %r9,%r10,__LC_SYSTEM_TIMER - mvc __LC_LAST_UPDATE_TIMER(8),__VQ_IDLE_EXIT(%r3) - # prepare return psw - n %r8,BASED(cleanup_idle_wait) # clear wait state bit - l %r9,24(%r11) # return from psw_idle - br %r14 -cleanup_idle_insn: - .long psw_idle_lpsw + 0x80000000 -cleanup_idle_wait: - .long 0xfffdffff - -/* - * Integer constants - */ - .align 4 -.Lnr_syscalls: - .long NR_syscalls -.Lvtimer_max: - .quad 0x7fffffffffffffff - -/* - * Symbol constants - */ -.Ldo_machine_check: .long s390_do_machine_check -.Lhandle_mcck: .long s390_handle_mcck -.Ldo_IRQ: .long do_IRQ -.Ldo_extint: .long do_extint -.Ldo_signal: .long do_signal -.Ldo_notify_resume: .long do_notify_resume -.Ldo_per_trap: .long do_per_trap -.Ldo_execve: .long do_execve -.Lexecve_tail: .long execve_tail -.Ljump_table: .long pgm_check_table -.Lschedule: .long schedule -#ifdef CONFIG_PREEMPT -.Lpreempt_irq: .long preempt_schedule_irq -#endif -.Ltrace_enter: .long do_syscall_trace_enter -.Ltrace_exit: .long do_syscall_trace_exit -.Lschedule_tail: .long schedule_tail -.Lsys_call_table: .long sys_call_table -.Lsysc_per: .long sysc_per + 0x80000000 -#ifdef CONFIG_TRACE_IRQFLAGS -.Lhardirqs_on: .long trace_hardirqs_on_caller -.Lhardirqs_off: .long trace_hardirqs_off_caller -#endif -#ifdef CONFIG_LOCKDEP -.Llockdep_sys_exit: .long lockdep_sys_exit -#endif -.Lcritical_start: .long __critical_start + 0x80000000 -.Lcritical_length: .long __critical_end - __critical_start - - .section .rodata, "a" -#define SYSCALL(esa,esame,emu) .long esa - .globl sys_call_table -sys_call_table: -#include "syscalls.S" -#undef SYSCALL diff --git a/ANDROID_3.4.5/arch/s390/kernel/entry.h b/ANDROID_3.4.5/arch/s390/kernel/entry.h deleted file mode 100644 index 6cdddac9..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/entry.h +++ /dev/null @@ -1,75 +0,0 @@ -#ifndef _ENTRY_H -#define _ENTRY_H - -#include <linux/types.h> -#include <linux/signal.h> -#include <asm/ptrace.h> -#include <asm/cputime.h> -#include <asm/timer.h> - -extern void (*pgm_check_table[128])(struct pt_regs *); -extern void *restart_stack; - -void system_call(void); -void pgm_check_handler(void); -void ext_int_handler(void); -void io_int_handler(void); -void mcck_int_handler(void); -void restart_int_handler(void); -void restart_call_handler(void); -void psw_idle(struct s390_idle_data *, struct vtimer_queue *, - unsigned long, int); - -asmlinkage long do_syscall_trace_enter(struct pt_regs *regs); -asmlinkage void do_syscall_trace_exit(struct pt_regs *regs); - -void do_protection_exception(struct pt_regs *regs); -void do_dat_exception(struct pt_regs *regs); -void do_asce_exception(struct pt_regs *regs); - -void do_per_trap(struct pt_regs *regs); -void syscall_trace(struct pt_regs *regs, int entryexit); -void kernel_stack_overflow(struct pt_regs * regs); -void do_signal(struct pt_regs *regs); -int handle_signal32(unsigned long sig, struct k_sigaction *ka, - siginfo_t *info, sigset_t *oldset, struct pt_regs *regs); -void do_notify_resume(struct pt_regs *regs); - -struct ext_code; -void do_extint(struct pt_regs *regs, struct ext_code, unsigned int, unsigned long); -void do_restart(void); -void __init startup_init(void); -void die(struct pt_regs *regs, const char *str); - -void __init time_init(void); - -struct s390_mmap_arg_struct; -struct fadvise64_64_args; -struct old_sigaction; - -long sys_mmap2(struct s390_mmap_arg_struct __user *arg); -long sys_s390_ipc(uint call, int first, unsigned long second, - unsigned long third, void __user *ptr); -long sys_s390_personality(unsigned int personality); -long sys_s390_fadvise64(int fd, u32 offset_high, u32 offset_low, - size_t len, int advice); -long sys_s390_fadvise64_64(struct fadvise64_64_args __user *args); -long sys_s390_fallocate(int fd, int mode, loff_t offset, u32 len_high, - u32 len_low); -long sys_fork(void); -long sys_clone(unsigned long newsp, unsigned long clone_flags, - int __user *parent_tidptr, int __user *child_tidptr); -long sys_vfork(void); -void execve_tail(void); -long sys_execve(const char __user *name, const char __user *const __user *argv, - const char __user *const __user *envp); -long sys_sigsuspend(int history0, int history1, old_sigset_t mask); -long sys_sigaction(int sig, const struct old_sigaction __user *act, - struct old_sigaction __user *oact); -long sys_sigaltstack(const stack_t __user *uss, stack_t __user *uoss); -long sys_sigreturn(void); -long sys_rt_sigreturn(void); -long sys32_sigreturn(void); -long sys32_rt_sigreturn(void); - -#endif /* _ENTRY_H */ diff --git a/ANDROID_3.4.5/arch/s390/kernel/entry64.S b/ANDROID_3.4.5/arch/s390/kernel/entry64.S deleted file mode 100644 index 4e1c292f..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/entry64.S +++ /dev/null @@ -1,1030 +0,0 @@ -/* - * arch/s390/kernel/entry64.S - * S390 low-level entry points. - * - * Copyright (C) IBM Corp. 1999,2012 - * Author(s): Martin Schwidefsky (schwidefsky@de.ibm.com), - * Hartmut Penner (hp@de.ibm.com), - * Denis Joseph Barrow (djbarrow@de.ibm.com,barrow_dj@yahoo.com), - * Heiko Carstens <heiko.carstens@de.ibm.com> - */ - -#include <linux/init.h> -#include <linux/linkage.h> -#include <asm/cache.h> -#include <asm/errno.h> -#include <asm/ptrace.h> -#include <asm/thread_info.h> -#include <asm/asm-offsets.h> -#include <asm/unistd.h> -#include <asm/page.h> - -__PT_R0 = __PT_GPRS -__PT_R1 = __PT_GPRS + 8 -__PT_R2 = __PT_GPRS + 16 -__PT_R3 = __PT_GPRS + 24 -__PT_R4 = __PT_GPRS + 32 -__PT_R5 = __PT_GPRS + 40 -__PT_R6 = __PT_GPRS + 48 -__PT_R7 = __PT_GPRS + 56 -__PT_R8 = __PT_GPRS + 64 -__PT_R9 = __PT_GPRS + 72 -__PT_R10 = __PT_GPRS + 80 -__PT_R11 = __PT_GPRS + 88 -__PT_R12 = __PT_GPRS + 96 -__PT_R13 = __PT_GPRS + 104 -__PT_R14 = __PT_GPRS + 112 -__PT_R15 = __PT_GPRS + 120 - -STACK_SHIFT = PAGE_SHIFT + THREAD_ORDER -STACK_SIZE = 1 << STACK_SHIFT - -_TIF_WORK_SVC = (_TIF_SIGPENDING | _TIF_NOTIFY_RESUME | _TIF_NEED_RESCHED | \ - _TIF_MCCK_PENDING | _TIF_PER_TRAP ) -_TIF_WORK_INT = (_TIF_SIGPENDING | _TIF_NOTIFY_RESUME | _TIF_NEED_RESCHED | \ - _TIF_MCCK_PENDING) -_TIF_TRACE = (_TIF_SYSCALL_TRACE | _TIF_SYSCALL_AUDIT | _TIF_SECCOMP | \ - _TIF_SYSCALL_TRACEPOINT) -_TIF_EXIT_SIE = (_TIF_SIGPENDING | _TIF_NEED_RESCHED | _TIF_MCCK_PENDING) - -#define BASED(name) name-system_call(%r13) - - .macro TRACE_IRQS_ON -#ifdef CONFIG_TRACE_IRQFLAGS - basr %r2,%r0 - brasl %r14,trace_hardirqs_on_caller -#endif - .endm - - .macro TRACE_IRQS_OFF -#ifdef CONFIG_TRACE_IRQFLAGS - basr %r2,%r0 - brasl %r14,trace_hardirqs_off_caller -#endif - .endm - - .macro LOCKDEP_SYS_EXIT -#ifdef CONFIG_LOCKDEP - tm __PT_PSW+1(%r11),0x01 # returning to user ? - jz .+10 - brasl %r14,lockdep_sys_exit -#endif - .endm - - .macro SPP newpp -#if defined(CONFIG_KVM) || defined(CONFIG_KVM_MODULE) - tm __LC_MACHINE_FLAGS+6,0x20 # MACHINE_FLAG_SPP - jz .+8 - .insn s,0xb2800000,\newpp -#endif - .endm - - .macro HANDLE_SIE_INTERCEPT scratch -#if defined(CONFIG_KVM) || defined(CONFIG_KVM_MODULE) - tm __TI_flags+6(%r12),_TIF_SIE>>8 - jz .+42 - tm __LC_MACHINE_FLAGS+6,0x20 # MACHINE_FLAG_SPP - jz .+8 - .insn s,0xb2800000,BASED(.Lhost_id) # set host id - lgr \scratch,%r9 - slg \scratch,BASED(.Lsie_loop) - clg \scratch,BASED(.Lsie_length) - jhe .+10 - lg %r9,BASED(.Lsie_loop) -#endif - .endm - - .macro CHECK_STACK stacksize,savearea -#ifdef CONFIG_CHECK_STACK - tml %r15,\stacksize - CONFIG_STACK_GUARD - lghi %r14,\savearea - jz stack_overflow -#endif - .endm - - .macro SWITCH_ASYNC savearea,stack,shift - tmhh %r8,0x0001 # interrupting from user ? - jnz 1f - lgr %r14,%r9 - slg %r14,BASED(.Lcritical_start) - clg %r14,BASED(.Lcritical_length) - jhe 0f - lghi %r11,\savearea # inside critical section, do cleanup - brasl %r14,cleanup_critical - tmhh %r8,0x0001 # retest problem state after cleanup - jnz 1f -0: lg %r14,\stack # are we already on the target stack? - slgr %r14,%r15 - srag %r14,%r14,\shift - jnz 1f - CHECK_STACK 1<<\shift,\savearea - j 2f -1: lg %r15,\stack # load target stack -2: aghi %r15,-(STACK_FRAME_OVERHEAD + __PT_SIZE) - la %r11,STACK_FRAME_OVERHEAD(%r15) - .endm - - .macro UPDATE_VTIME scratch,enter_timer - lg \scratch,__LC_EXIT_TIMER - slg \scratch,\enter_timer - alg \scratch,__LC_USER_TIMER - stg \scratch,__LC_USER_TIMER - lg \scratch,__LC_LAST_UPDATE_TIMER - slg \scratch,__LC_EXIT_TIMER - alg \scratch,__LC_SYSTEM_TIMER - stg \scratch,__LC_SYSTEM_TIMER - mvc __LC_LAST_UPDATE_TIMER(8),\enter_timer - .endm - - .macro LAST_BREAK scratch - srag \scratch,%r10,23 - jz .+10 - stg %r10,__TI_last_break(%r12) - .endm - - .macro REENABLE_IRQS - stg %r8,__LC_RETURN_PSW - ni __LC_RETURN_PSW,0xbf - ssm __LC_RETURN_PSW - .endm - - .section .kprobes.text, "ax" - -/* - * Scheduler resume function, called by switch_to - * gpr2 = (task_struct *) prev - * gpr3 = (task_struct *) next - * Returns: - * gpr2 = prev - */ -ENTRY(__switch_to) - lg %r4,__THREAD_info(%r2) # get thread_info of prev - lg %r5,__THREAD_info(%r3) # get thread_info of next - tm __TI_flags+7(%r4),_TIF_MCCK_PENDING # machine check pending? - jz 0f - ni __TI_flags+7(%r4),255-_TIF_MCCK_PENDING # clear flag in prev - oi __TI_flags+7(%r5),_TIF_MCCK_PENDING # set it in next -0: stmg %r6,%r15,__SF_GPRS(%r15) # store gprs of prev task - stg %r15,__THREAD_ksp(%r2) # store kernel stack of prev - lg %r15,__THREAD_ksp(%r3) # load kernel stack of next - lctl %c4,%c4,__TASK_pid(%r3) # load pid to control reg. 4 - lmg %r6,%r15,__SF_GPRS(%r15) # load gprs of next task - stg %r3,__LC_CURRENT # store task struct of next - mvc __LC_CURRENT_PID+4(4,%r0),__TASK_pid(%r3) # store pid of next - stg %r5,__LC_THREAD_INFO # store thread info of next - aghi %r5,STACK_SIZE # end of kernel stack of next - stg %r5,__LC_KERNEL_STACK # store end of kernel stack - br %r14 - -__critical_start: -/* - * SVC interrupt handler routine. System calls are synchronous events and - * are executed with interrupts enabled. - */ - -ENTRY(system_call) - stpt __LC_SYNC_ENTER_TIMER -sysc_stmg: - stmg %r8,%r15,__LC_SAVE_AREA_SYNC - lg %r10,__LC_LAST_BREAK - lg %r12,__LC_THREAD_INFO - larl %r13,system_call -sysc_per: - lg %r15,__LC_KERNEL_STACK - aghi %r15,-(STACK_FRAME_OVERHEAD + __PT_SIZE) - la %r11,STACK_FRAME_OVERHEAD(%r15) # pointer to pt_regs -sysc_vtime: - UPDATE_VTIME %r13,__LC_SYNC_ENTER_TIMER - LAST_BREAK %r13 - stmg %r0,%r7,__PT_R0(%r11) - mvc __PT_R8(64,%r11),__LC_SAVE_AREA_SYNC - mvc __PT_PSW(16,%r11),__LC_SVC_OLD_PSW - mvc __PT_INT_CODE(4,%r11),__LC_SVC_ILC -sysc_do_svc: - oi __TI_flags+7(%r12),_TIF_SYSCALL - llgh %r8,__PT_INT_CODE+2(%r11) - slag %r8,%r8,2 # shift and test for svc 0 - jnz sysc_nr_ok - # svc 0: system call number in %r1 - llgfr %r1,%r1 # clear high word in r1 - cghi %r1,NR_syscalls - jnl sysc_nr_ok - sth %r1,__PT_INT_CODE+2(%r11) - slag %r8,%r1,2 -sysc_nr_ok: - larl %r10,sys_call_table # 64 bit system call table -#ifdef CONFIG_COMPAT - tm __TI_flags+5(%r12),(_TIF_31BIT>>16) - jno sysc_noemu - larl %r10,sys_call_table_emu # 31 bit system call table -sysc_noemu: -#endif - xc __SF_BACKCHAIN(8,%r15),__SF_BACKCHAIN(%r15) - stg %r2,__PT_ORIG_GPR2(%r11) - stg %r7,STACK_FRAME_OVERHEAD(%r15) - lgf %r9,0(%r8,%r10) # get system call add. - tm __TI_flags+6(%r12),_TIF_TRACE >> 8 - jnz sysc_tracesys - basr %r14,%r9 # call sys_xxxx - stg %r2,__PT_R2(%r11) # store return value - -sysc_return: - LOCKDEP_SYS_EXIT -sysc_tif: - tm __PT_PSW+1(%r11),0x01 # returning to user ? - jno sysc_restore - tm __TI_flags+7(%r12),_TIF_WORK_SVC - jnz sysc_work # check for work - ni __TI_flags+7(%r12),255-_TIF_SYSCALL -sysc_restore: - lg %r14,__LC_VDSO_PER_CPU - lmg %r0,%r10,__PT_R0(%r11) - mvc __LC_RETURN_PSW(16),__PT_PSW(%r11) - stpt __LC_EXIT_TIMER - mvc __VDSO_ECTG_BASE(16,%r14),__LC_EXIT_TIMER - lmg %r11,%r15,__PT_R11(%r11) - lpswe __LC_RETURN_PSW -sysc_done: - -# -# One of the work bits is on. Find out which one. -# -sysc_work: - tm __TI_flags+7(%r12),_TIF_MCCK_PENDING - jo sysc_mcck_pending - tm __TI_flags+7(%r12),_TIF_NEED_RESCHED - jo sysc_reschedule - tm __TI_flags+7(%r12),_TIF_SIGPENDING - jo sysc_sigpending - tm __TI_flags+7(%r12),_TIF_NOTIFY_RESUME - jo sysc_notify_resume - tm __TI_flags+7(%r12),_TIF_PER_TRAP - jo sysc_singlestep - j sysc_return # beware of critical section cleanup - -# -# _TIF_NEED_RESCHED is set, call schedule -# -sysc_reschedule: - larl %r14,sysc_return - jg schedule - -# -# _TIF_MCCK_PENDING is set, call handler -# -sysc_mcck_pending: - larl %r14,sysc_return - jg s390_handle_mcck # TIF bit will be cleared by handler - -# -# _TIF_SIGPENDING is set, call do_signal -# -sysc_sigpending: - ni __TI_flags+7(%r12),255-_TIF_PER_TRAP # clear TIF_PER_TRAP - lgr %r2,%r11 # pass pointer to pt_regs - brasl %r14,do_signal - tm __TI_flags+7(%r12),_TIF_SYSCALL - jno sysc_return - lmg %r2,%r7,__PT_R2(%r11) # load svc arguments - lghi %r8,0 # svc 0 returns -ENOSYS - lh %r1,__PT_INT_CODE+2(%r11) # load new svc number - cghi %r1,NR_syscalls - jnl sysc_nr_ok # invalid svc number -> do svc 0 - slag %r8,%r1,2 - j sysc_nr_ok # restart svc - -# -# _TIF_NOTIFY_RESUME is set, call do_notify_resume -# -sysc_notify_resume: - lgr %r2,%r11 # pass pointer to pt_regs - larl %r14,sysc_return - jg do_notify_resume - -# -# _TIF_PER_TRAP is set, call do_per_trap -# -sysc_singlestep: - ni __TI_flags+7(%r12),255-(_TIF_SYSCALL | _TIF_PER_TRAP) - lgr %r2,%r11 # pass pointer to pt_regs - larl %r14,sysc_return - jg do_per_trap - -# -# call tracehook_report_syscall_entry/tracehook_report_syscall_exit before -# and after the system call -# -sysc_tracesys: - lgr %r2,%r11 # pass pointer to pt_regs - la %r3,0 - llgh %r0,__PT_INT_CODE+2(%r11) - stg %r0,__PT_R2(%r11) - brasl %r14,do_syscall_trace_enter - lghi %r0,NR_syscalls - clgr %r0,%r2 - jnh sysc_tracenogo - sllg %r8,%r2,2 - lgf %r9,0(%r8,%r10) -sysc_tracego: - lmg %r3,%r7,__PT_R3(%r11) - stg %r7,STACK_FRAME_OVERHEAD(%r15) - lg %r2,__PT_ORIG_GPR2(%r11) - basr %r14,%r9 # call sys_xxx - stg %r2,__PT_R2(%r11) # store return value -sysc_tracenogo: - tm __TI_flags+6(%r12),_TIF_TRACE >> 8 - jz sysc_return - lgr %r2,%r11 # pass pointer to pt_regs - larl %r14,sysc_return - jg do_syscall_trace_exit - -# -# a new process exits the kernel with ret_from_fork -# -ENTRY(ret_from_fork) - la %r11,STACK_FRAME_OVERHEAD(%r15) - lg %r12,__LC_THREAD_INFO - tm __PT_PSW+1(%r11),0x01 # forking a kernel thread ? - jo 0f - stg %r15,__PT_R15(%r11) # store stack pointer for new kthread -0: brasl %r14,schedule_tail - TRACE_IRQS_ON - ssm __LC_SVC_NEW_PSW # reenable interrupts - j sysc_tracenogo - -# -# kernel_execve function needs to deal with pt_regs that is not -# at the usual place -# -ENTRY(kernel_execve) - stmg %r12,%r15,96(%r15) - lgr %r14,%r15 - aghi %r15,-(STACK_FRAME_OVERHEAD + __PT_SIZE) - stg %r14,__SF_BACKCHAIN(%r15) - la %r12,STACK_FRAME_OVERHEAD(%r15) - xc 0(__PT_SIZE,%r12),0(%r12) - lgr %r5,%r12 - brasl %r14,do_execve - ltgfr %r2,%r2 - je 0f - aghi %r15,(STACK_FRAME_OVERHEAD + __PT_SIZE) - lmg %r12,%r15,96(%r15) - br %r14 - # execve succeeded. -0: ssm __LC_PGM_NEW_PSW # disable I/O and ext. interrupts - lg %r15,__LC_KERNEL_STACK # load ksp - aghi %r15,-(STACK_FRAME_OVERHEAD + __PT_SIZE) - la %r11,STACK_FRAME_OVERHEAD(%r15) - mvc 0(__PT_SIZE,%r11),0(%r12) # copy pt_regs - lg %r12,__LC_THREAD_INFO - xc __SF_BACKCHAIN(8,%r15),__SF_BACKCHAIN(%r15) - ssm __LC_SVC_NEW_PSW # reenable interrupts - brasl %r14,execve_tail - j sysc_return - -/* - * Program check handler routine - */ - -ENTRY(pgm_check_handler) - stpt __LC_SYNC_ENTER_TIMER - stmg %r8,%r15,__LC_SAVE_AREA_SYNC - lg %r10,__LC_LAST_BREAK - lg %r12,__LC_THREAD_INFO - larl %r13,system_call - lmg %r8,%r9,__LC_PGM_OLD_PSW - HANDLE_SIE_INTERCEPT %r14 - tmhh %r8,0x0001 # test problem state bit - jnz 1f # -> fault in user space - tmhh %r8,0x4000 # PER bit set in old PSW ? - jnz 0f # -> enabled, can't be a double fault - tm __LC_PGM_ILC+3,0x80 # check for per exception - jnz pgm_svcper # -> single stepped svc -0: CHECK_STACK STACK_SIZE,__LC_SAVE_AREA_SYNC - j 2f -1: UPDATE_VTIME %r14,__LC_SYNC_ENTER_TIMER - LAST_BREAK %r14 - lg %r15,__LC_KERNEL_STACK -2: aghi %r15,-(STACK_FRAME_OVERHEAD + __PT_SIZE) - la %r11,STACK_FRAME_OVERHEAD(%r15) - stmg %r0,%r7,__PT_R0(%r11) - mvc __PT_R8(64,%r11),__LC_SAVE_AREA_SYNC - stmg %r8,%r9,__PT_PSW(%r11) - mvc __PT_INT_CODE(4,%r11),__LC_PGM_ILC - mvc __PT_INT_PARM_LONG(8,%r11),__LC_TRANS_EXC_CODE - stg %r10,__PT_ARGS(%r11) - tm __LC_PGM_ILC+3,0x80 # check for per exception - jz 0f - lg %r1,__TI_task(%r12) - tmhh %r8,0x0001 # kernel per event ? - jz pgm_kprobe - oi __TI_flags+7(%r12),_TIF_PER_TRAP - mvc __THREAD_per_address(8,%r1),__LC_PER_ADDRESS - mvc __THREAD_per_cause(2,%r1),__LC_PER_CAUSE - mvc __THREAD_per_paid(1,%r1),__LC_PER_PAID -0: REENABLE_IRQS - xc __SF_BACKCHAIN(8,%r15),__SF_BACKCHAIN(%r15) - larl %r1,pgm_check_table - llgh %r10,__PT_INT_CODE+2(%r11) - nill %r10,0x007f - sll %r10,3 - je sysc_return - lg %r1,0(%r10,%r1) # load address of handler routine - lgr %r2,%r11 # pass pointer to pt_regs - basr %r14,%r1 # branch to interrupt-handler - j sysc_return - -# -# PER event in supervisor state, must be kprobes -# -pgm_kprobe: - REENABLE_IRQS - xc __SF_BACKCHAIN(8,%r15),__SF_BACKCHAIN(%r15) - lgr %r2,%r11 # pass pointer to pt_regs - brasl %r14,do_per_trap - j sysc_return - -# -# single stepped system call -# -pgm_svcper: - oi __TI_flags+7(%r12),_TIF_PER_TRAP - mvc __LC_RETURN_PSW(8),__LC_SVC_NEW_PSW - larl %r14,sysc_per - stg %r14,__LC_RETURN_PSW+8 - lpswe __LC_RETURN_PSW # branch to sysc_per and enable irqs - -/* - * IO interrupt handler routine - */ -ENTRY(io_int_handler) - stck __LC_INT_CLOCK - stpt __LC_ASYNC_ENTER_TIMER - stmg %r8,%r15,__LC_SAVE_AREA_ASYNC - lg %r10,__LC_LAST_BREAK - lg %r12,__LC_THREAD_INFO - larl %r13,system_call - lmg %r8,%r9,__LC_IO_OLD_PSW - HANDLE_SIE_INTERCEPT %r14 - SWITCH_ASYNC __LC_SAVE_AREA_ASYNC,__LC_ASYNC_STACK,STACK_SHIFT - tmhh %r8,0x0001 # interrupting from user? - jz io_skip - UPDATE_VTIME %r14,__LC_ASYNC_ENTER_TIMER - LAST_BREAK %r14 -io_skip: - stmg %r0,%r7,__PT_R0(%r11) - mvc __PT_R8(64,%r11),__LC_SAVE_AREA_ASYNC - stmg %r8,%r9,__PT_PSW(%r11) - TRACE_IRQS_OFF - xc __SF_BACKCHAIN(8,%r15),__SF_BACKCHAIN(%r15) - lgr %r2,%r11 # pass pointer to pt_regs - brasl %r14,do_IRQ -io_return: - LOCKDEP_SYS_EXIT - TRACE_IRQS_ON -io_tif: - tm __TI_flags+7(%r12),_TIF_WORK_INT - jnz io_work # there is work to do (signals etc.) -io_restore: - lg %r14,__LC_VDSO_PER_CPU - lmg %r0,%r10,__PT_R0(%r11) - mvc __LC_RETURN_PSW(16),__PT_PSW(%r11) - stpt __LC_EXIT_TIMER - mvc __VDSO_ECTG_BASE(16,%r14),__LC_EXIT_TIMER - lmg %r11,%r15,__PT_R11(%r11) - lpswe __LC_RETURN_PSW -io_done: - -# -# There is work todo, find out in which context we have been interrupted: -# 1) if we return to user space we can do all _TIF_WORK_INT work -# 2) if we return to kernel code and kvm is enabled check if we need to -# modify the psw to leave SIE -# 3) if we return to kernel code and preemptive scheduling is enabled check -# the preemption counter and if it is zero call preempt_schedule_irq -# Before any work can be done, a switch to the kernel stack is required. -# -io_work: - tm __PT_PSW+1(%r11),0x01 # returning to user ? - jo io_work_user # yes -> do resched & signal -#ifdef CONFIG_PREEMPT - # check for preemptive scheduling - icm %r0,15,__TI_precount(%r12) - jnz io_restore # preemption is disabled - tm __TI_flags+7(%r12),_TIF_NEED_RESCHED - jno io_restore - # switch to kernel stack - lg %r1,__PT_R15(%r11) - aghi %r1,-(STACK_FRAME_OVERHEAD + __PT_SIZE) - mvc STACK_FRAME_OVERHEAD(__PT_SIZE,%r1),0(%r11) - xc __SF_BACKCHAIN(8,%r1),__SF_BACKCHAIN(%r1) - la %r11,STACK_FRAME_OVERHEAD(%r1) - lgr %r15,%r1 - # TRACE_IRQS_ON already done at io_return, call - # TRACE_IRQS_OFF to keep things symmetrical - TRACE_IRQS_OFF - brasl %r14,preempt_schedule_irq - j io_return -#else - j io_restore -#endif - -# -# Need to do work before returning to userspace, switch to kernel stack -# -io_work_user: - lg %r1,__LC_KERNEL_STACK - aghi %r1,-(STACK_FRAME_OVERHEAD + __PT_SIZE) - mvc STACK_FRAME_OVERHEAD(__PT_SIZE,%r1),0(%r11) - xc __SF_BACKCHAIN(8,%r1),__SF_BACKCHAIN(%r1) - la %r11,STACK_FRAME_OVERHEAD(%r1) - lgr %r15,%r1 - -# -# One of the work bits is on. Find out which one. -# Checked are: _TIF_SIGPENDING, _TIF_NOTIFY_RESUME, _TIF_NEED_RESCHED -# and _TIF_MCCK_PENDING -# -io_work_tif: - tm __TI_flags+7(%r12),_TIF_MCCK_PENDING - jo io_mcck_pending - tm __TI_flags+7(%r12),_TIF_NEED_RESCHED - jo io_reschedule - tm __TI_flags+7(%r12),_TIF_SIGPENDING - jo io_sigpending - tm __TI_flags+7(%r12),_TIF_NOTIFY_RESUME - jo io_notify_resume - j io_return # beware of critical section cleanup - -# -# _TIF_MCCK_PENDING is set, call handler -# -io_mcck_pending: - # TRACE_IRQS_ON already done at io_return - brasl %r14,s390_handle_mcck # TIF bit will be cleared by handler - TRACE_IRQS_OFF - j io_return - -# -# _TIF_NEED_RESCHED is set, call schedule -# -io_reschedule: - # TRACE_IRQS_ON already done at io_return - ssm __LC_SVC_NEW_PSW # reenable interrupts - brasl %r14,schedule # call scheduler - ssm __LC_PGM_NEW_PSW # disable I/O and ext. interrupts - TRACE_IRQS_OFF - j io_return - -# -# _TIF_SIGPENDING or is set, call do_signal -# -io_sigpending: - # TRACE_IRQS_ON already done at io_return - ssm __LC_SVC_NEW_PSW # reenable interrupts - lgr %r2,%r11 # pass pointer to pt_regs - brasl %r14,do_signal - ssm __LC_PGM_NEW_PSW # disable I/O and ext. interrupts - TRACE_IRQS_OFF - j io_return - -# -# _TIF_NOTIFY_RESUME or is set, call do_notify_resume -# -io_notify_resume: - # TRACE_IRQS_ON already done at io_return - ssm __LC_SVC_NEW_PSW # reenable interrupts - lgr %r2,%r11 # pass pointer to pt_regs - brasl %r14,do_notify_resume - ssm __LC_PGM_NEW_PSW # disable I/O and ext. interrupts - TRACE_IRQS_OFF - j io_return - -/* - * External interrupt handler routine - */ -ENTRY(ext_int_handler) - stck __LC_INT_CLOCK - stpt __LC_ASYNC_ENTER_TIMER - stmg %r8,%r15,__LC_SAVE_AREA_ASYNC - lg %r10,__LC_LAST_BREAK - lg %r12,__LC_THREAD_INFO - larl %r13,system_call - lmg %r8,%r9,__LC_EXT_OLD_PSW - HANDLE_SIE_INTERCEPT %r14 - SWITCH_ASYNC __LC_SAVE_AREA_ASYNC,__LC_ASYNC_STACK,STACK_SHIFT - tmhh %r8,0x0001 # interrupting from user ? - jz ext_skip - UPDATE_VTIME %r14,__LC_ASYNC_ENTER_TIMER - LAST_BREAK %r14 -ext_skip: - stmg %r0,%r7,__PT_R0(%r11) - mvc __PT_R8(64,%r11),__LC_SAVE_AREA_ASYNC - stmg %r8,%r9,__PT_PSW(%r11) - TRACE_IRQS_OFF - lghi %r1,4096 - lgr %r2,%r11 # pass pointer to pt_regs - llgf %r3,__LC_EXT_CPU_ADDR # get cpu address + interruption code - llgf %r4,__LC_EXT_PARAMS # get external parameter - lg %r5,__LC_EXT_PARAMS2-4096(%r1) # get 64 bit external parameter - brasl %r14,do_extint - j io_return - -/* - * Load idle PSW. The second "half" of this function is in cleanup_idle. - */ -ENTRY(psw_idle) - stg %r4,__SF_EMPTY(%r15) - larl %r1,psw_idle_lpsw+4 - stg %r1,__SF_EMPTY+8(%r15) - larl %r1,.Lvtimer_max - stck __IDLE_ENTER(%r2) - ltr %r5,%r5 - stpt __VQ_IDLE_ENTER(%r3) - jz psw_idle_lpsw - spt 0(%r1) -psw_idle_lpsw: - lpswe __SF_EMPTY(%r15) - br %r14 -psw_idle_end: - -__critical_end: - -/* - * Machine check handler routines - */ -ENTRY(mcck_int_handler) - stck __LC_MCCK_CLOCK - la %r1,4095 # revalidate r1 - spt __LC_CPU_TIMER_SAVE_AREA-4095(%r1) # revalidate cpu timer - lmg %r0,%r15,__LC_GPREGS_SAVE_AREA-4095(%r1)# revalidate gprs - lg %r10,__LC_LAST_BREAK - lg %r12,__LC_THREAD_INFO - larl %r13,system_call - lmg %r8,%r9,__LC_MCK_OLD_PSW - HANDLE_SIE_INTERCEPT %r14 - tm __LC_MCCK_CODE,0x80 # system damage? - jo mcck_panic # yes -> rest of mcck code invalid - lghi %r14,__LC_CPU_TIMER_SAVE_AREA - mvc __LC_MCCK_ENTER_TIMER(8),0(%r14) - tm __LC_MCCK_CODE+5,0x02 # stored cpu timer value valid? - jo 3f - la %r14,__LC_SYNC_ENTER_TIMER - clc 0(8,%r14),__LC_ASYNC_ENTER_TIMER - jl 0f - la %r14,__LC_ASYNC_ENTER_TIMER -0: clc 0(8,%r14),__LC_EXIT_TIMER - jl 1f - la %r14,__LC_EXIT_TIMER -1: clc 0(8,%r14),__LC_LAST_UPDATE_TIMER - jl 2f - la %r14,__LC_LAST_UPDATE_TIMER -2: spt 0(%r14) - mvc __LC_MCCK_ENTER_TIMER(8),0(%r14) -3: tm __LC_MCCK_CODE+2,0x09 # mwp + ia of old psw valid? - jno mcck_panic # no -> skip cleanup critical - SWITCH_ASYNC __LC_GPREGS_SAVE_AREA+64,__LC_PANIC_STACK,PAGE_SHIFT - tm %r8,0x0001 # interrupting from user ? - jz mcck_skip - UPDATE_VTIME %r14,__LC_MCCK_ENTER_TIMER - LAST_BREAK %r14 -mcck_skip: - lghi %r14,__LC_GPREGS_SAVE_AREA - mvc __PT_R0(128,%r11),0(%r14) - stmg %r8,%r9,__PT_PSW(%r11) - xc __SF_BACKCHAIN(8,%r15),__SF_BACKCHAIN(%r15) - lgr %r2,%r11 # pass pointer to pt_regs - brasl %r14,s390_do_machine_check - tm __PT_PSW+1(%r11),0x01 # returning to user ? - jno mcck_return - lg %r1,__LC_KERNEL_STACK # switch to kernel stack - aghi %r1,-(STACK_FRAME_OVERHEAD + __PT_SIZE) - mvc STACK_FRAME_OVERHEAD(__PT_SIZE,%r1),0(%r11) - xc __SF_BACKCHAIN(8,%r1),__SF_BACKCHAIN(%r1) - la %r11,STACK_FRAME_OVERHEAD(%r1) - lgr %r15,%r1 - ssm __LC_PGM_NEW_PSW # turn dat on, keep irqs off - tm __TI_flags+7(%r12),_TIF_MCCK_PENDING - jno mcck_return - TRACE_IRQS_OFF - brasl %r14,s390_handle_mcck - TRACE_IRQS_ON -mcck_return: - lg %r14,__LC_VDSO_PER_CPU - lmg %r0,%r10,__PT_R0(%r11) - mvc __LC_RETURN_MCCK_PSW(16),__PT_PSW(%r11) # move return PSW - tm __LC_RETURN_MCCK_PSW+1,0x01 # returning to user ? - jno 0f - stpt __LC_EXIT_TIMER - mvc __VDSO_ECTG_BASE(16,%r14),__LC_EXIT_TIMER -0: lmg %r11,%r15,__PT_R11(%r11) - lpswe __LC_RETURN_MCCK_PSW - -mcck_panic: - lg %r14,__LC_PANIC_STACK - slgr %r14,%r15 - srag %r14,%r14,PAGE_SHIFT - jz 0f - lg %r15,__LC_PANIC_STACK -0: aghi %r15,-(STACK_FRAME_OVERHEAD + __PT_SIZE) - j mcck_skip - -# -# PSW restart interrupt handler -# -ENTRY(restart_int_handler) - stg %r15,__LC_SAVE_AREA_RESTART - lg %r15,__LC_RESTART_STACK - aghi %r15,-__PT_SIZE # create pt_regs on stack - xc 0(__PT_SIZE,%r15),0(%r15) - stmg %r0,%r14,__PT_R0(%r15) - mvc __PT_R15(8,%r15),__LC_SAVE_AREA_RESTART - mvc __PT_PSW(16,%r15),__LC_RST_OLD_PSW # store restart old psw - aghi %r15,-STACK_FRAME_OVERHEAD # create stack frame on stack - xc 0(STACK_FRAME_OVERHEAD,%r15),0(%r15) - lmg %r1,%r3,__LC_RESTART_FN # load fn, parm & source cpu - ltgr %r3,%r3 # test source cpu address - jm 1f # negative -> skip source stop -0: sigp %r4,%r3,1 # sigp sense to source cpu - brc 10,0b # wait for status stored -1: basr %r14,%r1 # call function - stap __SF_EMPTY(%r15) # store cpu address - llgh %r3,__SF_EMPTY(%r15) -2: sigp %r4,%r3,5 # sigp stop to current cpu - brc 2,2b -3: j 3b - - .section .kprobes.text, "ax" - -#ifdef CONFIG_CHECK_STACK -/* - * The synchronous or the asynchronous stack overflowed. We are dead. - * No need to properly save the registers, we are going to panic anyway. - * Setup a pt_regs so that show_trace can provide a good call trace. - */ -stack_overflow: - lg %r11,__LC_PANIC_STACK # change to panic stack - aghi %r11,-__PT_SIZE # create pt_regs - stmg %r0,%r7,__PT_R0(%r11) - stmg %r8,%r9,__PT_PSW(%r11) - mvc __PT_R8(64,%r11),0(%r14) - stg %r10,__PT_ORIG_GPR2(%r11) # store last break to orig_gpr2 - lgr %r15,%r11 - aghi %r15,-STACK_FRAME_OVERHEAD - xc __SF_BACKCHAIN(8,%r15),__SF_BACKCHAIN(%r15) - lgr %r2,%r11 # pass pointer to pt_regs - jg kernel_stack_overflow -#endif - - .align 8 -cleanup_table: - .quad system_call - .quad sysc_do_svc - .quad sysc_tif - .quad sysc_restore - .quad sysc_done - .quad io_tif - .quad io_restore - .quad io_done - .quad psw_idle - .quad psw_idle_end - -cleanup_critical: - clg %r9,BASED(cleanup_table) # system_call - jl 0f - clg %r9,BASED(cleanup_table+8) # sysc_do_svc - jl cleanup_system_call - clg %r9,BASED(cleanup_table+16) # sysc_tif - jl 0f - clg %r9,BASED(cleanup_table+24) # sysc_restore - jl cleanup_sysc_tif - clg %r9,BASED(cleanup_table+32) # sysc_done - jl cleanup_sysc_restore - clg %r9,BASED(cleanup_table+40) # io_tif - jl 0f - clg %r9,BASED(cleanup_table+48) # io_restore - jl cleanup_io_tif - clg %r9,BASED(cleanup_table+56) # io_done - jl cleanup_io_restore - clg %r9,BASED(cleanup_table+64) # psw_idle - jl 0f - clg %r9,BASED(cleanup_table+72) # psw_idle_end - jl cleanup_idle -0: br %r14 - - -cleanup_system_call: - # check if stpt has been executed - clg %r9,BASED(cleanup_system_call_insn) - jh 0f - mvc __LC_SYNC_ENTER_TIMER(8),__LC_ASYNC_ENTER_TIMER - cghi %r11,__LC_SAVE_AREA_ASYNC - je 0f - mvc __LC_SYNC_ENTER_TIMER(8),__LC_MCCK_ENTER_TIMER -0: # check if stmg has been executed - clg %r9,BASED(cleanup_system_call_insn+8) - jh 0f - mvc __LC_SAVE_AREA_SYNC(64),0(%r11) -0: # check if base register setup + TIF bit load has been done - clg %r9,BASED(cleanup_system_call_insn+16) - jhe 0f - # set up saved registers r10 and r12 - stg %r10,16(%r11) # r10 last break - stg %r12,32(%r11) # r12 thread-info pointer -0: # check if the user time update has been done - clg %r9,BASED(cleanup_system_call_insn+24) - jh 0f - lg %r15,__LC_EXIT_TIMER - slg %r15,__LC_SYNC_ENTER_TIMER - alg %r15,__LC_USER_TIMER - stg %r15,__LC_USER_TIMER -0: # check if the system time update has been done - clg %r9,BASED(cleanup_system_call_insn+32) - jh 0f - lg %r15,__LC_LAST_UPDATE_TIMER - slg %r15,__LC_EXIT_TIMER - alg %r15,__LC_SYSTEM_TIMER - stg %r15,__LC_SYSTEM_TIMER -0: # update accounting time stamp - mvc __LC_LAST_UPDATE_TIMER(8),__LC_SYNC_ENTER_TIMER - # do LAST_BREAK - lg %r9,16(%r11) - srag %r9,%r9,23 - jz 0f - mvc __TI_last_break(8,%r12),16(%r11) -0: # set up saved register r11 - lg %r15,__LC_KERNEL_STACK - aghi %r15,-__PT_SIZE - stg %r15,24(%r11) # r11 pt_regs pointer - # fill pt_regs - mvc __PT_R8(64,%r15),__LC_SAVE_AREA_SYNC - stmg %r0,%r7,__PT_R0(%r15) - mvc __PT_PSW(16,%r15),__LC_SVC_OLD_PSW - mvc __PT_INT_CODE(4,%r15),__LC_SVC_ILC - # setup saved register r15 - aghi %r15,-STACK_FRAME_OVERHEAD - stg %r15,56(%r11) # r15 stack pointer - # set new psw address and exit - larl %r9,sysc_do_svc - br %r14 -cleanup_system_call_insn: - .quad system_call - .quad sysc_stmg - .quad sysc_per - .quad sysc_vtime+18 - .quad sysc_vtime+42 - -cleanup_sysc_tif: - larl %r9,sysc_tif - br %r14 - -cleanup_sysc_restore: - clg %r9,BASED(cleanup_sysc_restore_insn) - je 0f - lg %r9,24(%r11) # get saved pointer to pt_regs - mvc __LC_RETURN_PSW(16),__PT_PSW(%r9) - mvc 0(64,%r11),__PT_R8(%r9) - lmg %r0,%r7,__PT_R0(%r9) -0: lmg %r8,%r9,__LC_RETURN_PSW - br %r14 -cleanup_sysc_restore_insn: - .quad sysc_done - 4 - -cleanup_io_tif: - larl %r9,io_tif - br %r14 - -cleanup_io_restore: - clg %r9,BASED(cleanup_io_restore_insn) - je 0f - lg %r9,24(%r11) # get saved r11 pointer to pt_regs - mvc __LC_RETURN_PSW(16),__PT_PSW(%r9) - mvc 0(64,%r11),__PT_R8(%r9) - lmg %r0,%r7,__PT_R0(%r9) -0: lmg %r8,%r9,__LC_RETURN_PSW - br %r14 -cleanup_io_restore_insn: - .quad io_done - 4 - -cleanup_idle: - # copy interrupt clock & cpu timer - mvc __IDLE_EXIT(8,%r2),__LC_INT_CLOCK - mvc __VQ_IDLE_EXIT(8,%r3),__LC_ASYNC_ENTER_TIMER - cghi %r11,__LC_SAVE_AREA_ASYNC - je 0f - mvc __IDLE_EXIT(8,%r2),__LC_MCCK_CLOCK - mvc __VQ_IDLE_EXIT(8,%r3),__LC_MCCK_ENTER_TIMER -0: # check if stck & stpt have been executed - clg %r9,BASED(cleanup_idle_insn) - jhe 1f - mvc __IDLE_ENTER(8,%r2),__IDLE_EXIT(%r2) - mvc __VQ_IDLE_ENTER(8,%r3),__VQ_IDLE_EXIT(%r3) - j 2f -1: # check if the cpu timer has been reprogrammed - ltr %r5,%r5 - jz 2f - spt __VQ_IDLE_ENTER(%r3) -2: # account system time going idle - lg %r9,__LC_STEAL_TIMER - alg %r9,__IDLE_ENTER(%r2) - slg %r9,__LC_LAST_UPDATE_CLOCK - stg %r9,__LC_STEAL_TIMER - mvc __LC_LAST_UPDATE_CLOCK(8),__IDLE_EXIT(%r2) - lg %r9,__LC_SYSTEM_TIMER - alg %r9,__LC_LAST_UPDATE_TIMER - slg %r9,__VQ_IDLE_ENTER(%r3) - stg %r9,__LC_SYSTEM_TIMER - mvc __LC_LAST_UPDATE_TIMER(8),__VQ_IDLE_EXIT(%r3) - # prepare return psw - nihh %r8,0xfffd # clear wait state bit - lg %r9,48(%r11) # return from psw_idle - br %r14 -cleanup_idle_insn: - .quad psw_idle_lpsw - -/* - * Integer constants - */ - .align 8 -.Lcritical_start: - .quad __critical_start -.Lcritical_length: - .quad __critical_end - __critical_start -.Lvtimer_max: - .quad 0x7fffffffffffffff - - -#if defined(CONFIG_KVM) || defined(CONFIG_KVM_MODULE) -/* - * sie64a calling convention: - * %r2 pointer to sie control block - * %r3 guest register save area - */ -ENTRY(sie64a) - stmg %r6,%r14,__SF_GPRS(%r15) # save kernel registers - stg %r2,__SF_EMPTY(%r15) # save control block pointer - stg %r3,__SF_EMPTY+8(%r15) # save guest register save area - xc __SF_EMPTY+16(8,%r15),__SF_EMPTY+16(%r15) # host id == 0 - lmg %r0,%r13,0(%r3) # load guest gprs 0-13 - lg %r14,__LC_THREAD_INFO # pointer thread_info struct - oi __TI_flags+6(%r14),_TIF_SIE>>8 -sie_loop: - lg %r14,__LC_THREAD_INFO # pointer thread_info struct - tm __TI_flags+7(%r14),_TIF_EXIT_SIE - jnz sie_exit - lg %r14,__LC_GMAP # get gmap pointer - ltgr %r14,%r14 - jz sie_gmap - lctlg %c1,%c1,__GMAP_ASCE(%r14) # load primary asce -sie_gmap: - lg %r14,__SF_EMPTY(%r15) # get control block pointer - SPP __SF_EMPTY(%r15) # set guest id - sie 0(%r14) -sie_done: - SPP __SF_EMPTY+16(%r15) # set host id - lg %r14,__LC_THREAD_INFO # pointer thread_info struct -sie_exit: - lctlg %c1,%c1,__LC_USER_ASCE # load primary asce - ni __TI_flags+6(%r14),255-(_TIF_SIE>>8) - lg %r14,__SF_EMPTY+8(%r15) # load guest register save area - stmg %r0,%r13,0(%r14) # save guest gprs 0-13 - lmg %r6,%r14,__SF_GPRS(%r15) # restore kernel registers - lghi %r2,0 - br %r14 -sie_fault: - lctlg %c1,%c1,__LC_USER_ASCE # load primary asce - lg %r14,__LC_THREAD_INFO # pointer thread_info struct - ni __TI_flags+6(%r14),255-(_TIF_SIE>>8) - lg %r14,__SF_EMPTY+8(%r15) # load guest register save area - stmg %r0,%r13,0(%r14) # save guest gprs 0-13 - lmg %r6,%r14,__SF_GPRS(%r15) # restore kernel registers - lghi %r2,-EFAULT - br %r14 - - .align 8 -.Lsie_loop: - .quad sie_loop -.Lsie_length: - .quad sie_done - sie_loop -.Lhost_id: - .quad 0 - - .section __ex_table,"a" - .quad sie_loop,sie_fault - .previous -#endif - - .section .rodata, "a" -#define SYSCALL(esa,esame,emu) .long esame - .globl sys_call_table -sys_call_table: -#include "syscalls.S" -#undef SYSCALL - -#ifdef CONFIG_COMPAT - -#define SYSCALL(esa,esame,emu) .long emu -sys_call_table_emu: -#include "syscalls.S" -#undef SYSCALL -#endif diff --git a/ANDROID_3.4.5/arch/s390/kernel/ftrace.c b/ANDROID_3.4.5/arch/s390/kernel/ftrace.c deleted file mode 100644 index 78bdf0e5..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/ftrace.c +++ /dev/null @@ -1,198 +0,0 @@ -/* - * Dynamic function tracer architecture backend. - * - * Copyright IBM Corp. 2009 - * - * Author(s): Heiko Carstens <heiko.carstens@de.ibm.com>, - * Martin Schwidefsky <schwidefsky@de.ibm.com> - */ - -#include <linux/hardirq.h> -#include <linux/uaccess.h> -#include <linux/ftrace.h> -#include <linux/kernel.h> -#include <linux/types.h> -#include <linux/kprobes.h> -#include <trace/syscall.h> -#include <asm/asm-offsets.h> - -#ifdef CONFIG_64BIT -#define MCOUNT_OFFSET_RET 12 -#else -#define MCOUNT_OFFSET_RET 22 -#endif - -#ifdef CONFIG_DYNAMIC_FTRACE - -void ftrace_disable_code(void); -void ftrace_enable_insn(void); - -#ifdef CONFIG_64BIT -/* - * The 64-bit mcount code looks like this: - * stg %r14,8(%r15) # offset 0 - * > larl %r1,<&counter> # offset 6 - * > brasl %r14,_mcount # offset 12 - * lg %r14,8(%r15) # offset 18 - * Total length is 24 bytes. The middle two instructions of the mcount - * block get overwritten by ftrace_make_nop / ftrace_make_call. - * The 64-bit enabled ftrace code block looks like this: - * stg %r14,8(%r15) # offset 0 - * > lg %r1,__LC_FTRACE_FUNC # offset 6 - * > lgr %r0,%r0 # offset 12 - * > basr %r14,%r1 # offset 16 - * lg %r14,8(%15) # offset 18 - * The return points of the mcount/ftrace function have the same offset 18. - * The 64-bit disable ftrace code block looks like this: - * stg %r14,8(%r15) # offset 0 - * > jg .+18 # offset 6 - * > lgr %r0,%r0 # offset 12 - * > basr %r14,%r1 # offset 16 - * lg %r14,8(%15) # offset 18 - * The jg instruction branches to offset 24 to skip as many instructions - * as possible. - */ -asm( - " .align 4\n" - "ftrace_disable_code:\n" - " jg 0f\n" - " lgr %r0,%r0\n" - " basr %r14,%r1\n" - "0:\n" - " .align 4\n" - "ftrace_enable_insn:\n" - " lg %r1,"__stringify(__LC_FTRACE_FUNC)"\n"); - -#define FTRACE_INSN_SIZE 6 - -#else /* CONFIG_64BIT */ -/* - * The 31-bit mcount code looks like this: - * st %r14,4(%r15) # offset 0 - * > bras %r1,0f # offset 4 - * > .long _mcount # offset 8 - * > .long <&counter> # offset 12 - * > 0: l %r14,0(%r1) # offset 16 - * > l %r1,4(%r1) # offset 20 - * basr %r14,%r14 # offset 24 - * l %r14,4(%r15) # offset 26 - * Total length is 30 bytes. The twenty bytes starting from offset 4 - * to offset 24 get overwritten by ftrace_make_nop / ftrace_make_call. - * The 31-bit enabled ftrace code block looks like this: - * st %r14,4(%r15) # offset 0 - * > l %r14,__LC_FTRACE_FUNC # offset 4 - * > j 0f # offset 8 - * > .fill 12,1,0x07 # offset 12 - * 0: basr %r14,%r14 # offset 24 - * l %r14,4(%r14) # offset 26 - * The return points of the mcount/ftrace function have the same offset 26. - * The 31-bit disabled ftrace code block looks like this: - * st %r14,4(%r15) # offset 0 - * > j .+26 # offset 4 - * > j 0f # offset 8 - * > .fill 12,1,0x07 # offset 12 - * 0: basr %r14,%r14 # offset 24 - * l %r14,4(%r14) # offset 26 - * The j instruction branches to offset 30 to skip as many instructions - * as possible. - */ -asm( - " .align 4\n" - "ftrace_disable_code:\n" - " j 1f\n" - " j 0f\n" - " .fill 12,1,0x07\n" - "0: basr %r14,%r14\n" - "1:\n" - " .align 4\n" - "ftrace_enable_insn:\n" - " l %r14,"__stringify(__LC_FTRACE_FUNC)"\n"); - -#define FTRACE_INSN_SIZE 4 - -#endif /* CONFIG_64BIT */ - - -int ftrace_make_nop(struct module *mod, struct dyn_ftrace *rec, - unsigned long addr) -{ - if (probe_kernel_write((void *) rec->ip, ftrace_disable_code, - MCOUNT_INSN_SIZE)) - return -EPERM; - return 0; -} - -int ftrace_make_call(struct dyn_ftrace *rec, unsigned long addr) -{ - if (probe_kernel_write((void *) rec->ip, ftrace_enable_insn, - FTRACE_INSN_SIZE)) - return -EPERM; - return 0; -} - -int ftrace_update_ftrace_func(ftrace_func_t func) -{ - return 0; -} - -int __init ftrace_dyn_arch_init(void *data) -{ - *(unsigned long *) data = 0; - return 0; -} - -#endif /* CONFIG_DYNAMIC_FTRACE */ - -#ifdef CONFIG_FUNCTION_GRAPH_TRACER -/* - * Hook the return address and push it in the stack of return addresses - * in current thread info. - */ -unsigned long __kprobes prepare_ftrace_return(unsigned long parent, - unsigned long ip) -{ - struct ftrace_graph_ent trace; - - if (unlikely(atomic_read(¤t->tracing_graph_pause))) - goto out; - if (ftrace_push_return_trace(parent, ip, &trace.depth, 0) == -EBUSY) - goto out; - trace.func = (ip & PSW_ADDR_INSN) - MCOUNT_OFFSET_RET; - /* Only trace if the calling function expects to. */ - if (!ftrace_graph_entry(&trace)) { - current->curr_ret_stack--; - goto out; - } - parent = (unsigned long) return_to_handler; -out: - return parent; -} - -#ifdef CONFIG_DYNAMIC_FTRACE -/* - * Patch the kernel code at ftrace_graph_caller location. The instruction - * there is branch relative and save to prepare_ftrace_return. To disable - * the call to prepare_ftrace_return we patch the bras offset to point - * directly after the instructions. To enable the call we calculate - * the original offset to prepare_ftrace_return and put it back. - */ -int ftrace_enable_ftrace_graph_caller(void) -{ - unsigned short offset; - - offset = ((void *) prepare_ftrace_return - - (void *) ftrace_graph_caller) / 2; - return probe_kernel_write(ftrace_graph_caller + 2, - &offset, sizeof(offset)); -} - -int ftrace_disable_ftrace_graph_caller(void) -{ - static unsigned short offset = 0x0002; - - return probe_kernel_write(ftrace_graph_caller + 2, - &offset, sizeof(offset)); -} - -#endif /* CONFIG_DYNAMIC_FTRACE */ -#endif /* CONFIG_FUNCTION_GRAPH_TRACER */ diff --git a/ANDROID_3.4.5/arch/s390/kernel/head.S b/ANDROID_3.4.5/arch/s390/kernel/head.S deleted file mode 100644 index adccd908..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/head.S +++ /dev/null @@ -1,571 +0,0 @@ -/* - * Copyright IBM Corp. 1999,2010 - * - * Author(s): Hartmut Penner <hp@de.ibm.com> - * Martin Schwidefsky <schwidefsky@de.ibm.com> - * Rob van der Heij <rvdhei@iae.nl> - * Heiko Carstens <heiko.carstens@de.ibm.com> - * - * There are 5 different IPL methods - * 1) load the image directly into ram at address 0 and do an PSW restart - * 2) linload will load the image from address 0x10000 to memory 0x10000 - * and start the code thru LPSW 0x0008000080010000 (VM only, deprecated) - * 3) generate the tape ipl header, store the generated image on a tape - * and ipl from it - * In case of SL tape you need to IPL 5 times to get past VOL1 etc - * 4) generate the vm reader ipl header, move the generated image to the - * VM reader (use option NOH!) and do a ipl from reader (VM only) - * 5) direct call of start by the SALIPL loader - * We use the cpuid to distinguish between VM and native ipl - * params for kernel are pushed to 0x10400 (see setup.h) - * - */ - -#include <linux/init.h> -#include <linux/linkage.h> -#include <asm/asm-offsets.h> -#include <asm/thread_info.h> -#include <asm/page.h> - -#ifdef CONFIG_64BIT -#define ARCH_OFFSET 4 -#else -#define ARCH_OFFSET 0 -#endif - -__HEAD -#ifndef CONFIG_IPL - .org 0 - .long 0x00080000,0x80000000+startup # Just a restart PSW -#else -#ifdef CONFIG_IPL_TAPE -#define IPL_BS 1024 - .org 0 - .long 0x00080000,0x80000000+iplstart # The first 24 bytes are loaded - .long 0x27000000,0x60000001 # by ipl to addresses 0-23. - .long 0x02000000,0x20000000+IPL_BS # (a PSW and two CCWs). - .long 0x00000000,0x00000000 # external old psw - .long 0x00000000,0x00000000 # svc old psw - .long 0x00000000,0x00000000 # program check old psw - .long 0x00000000,0x00000000 # machine check old psw - .long 0x00000000,0x00000000 # io old psw - .long 0x00000000,0x00000000 - .long 0x00000000,0x00000000 - .long 0x00000000,0x00000000 - .long 0x000a0000,0x00000058 # external new psw - .long 0x000a0000,0x00000060 # svc new psw - .long 0x000a0000,0x00000068 # program check new psw - .long 0x000a0000,0x00000070 # machine check new psw - .long 0x00080000,0x80000000+.Lioint # io new psw - - .org 0x100 -# -# subroutine for loading from tape -# Parameters: -# R1 = device number -# R2 = load address -.Lloader: - st %r14,.Lldret - la %r3,.Lorbread # r3 = address of orb - la %r5,.Lirb # r5 = address of irb - st %r2,.Lccwread+4 # initialize CCW data addresses - lctl %c6,%c6,.Lcr6 - slr %r2,%r2 -.Lldlp: - la %r6,3 # 3 retries -.Lssch: - ssch 0(%r3) # load chunk of IPL_BS bytes - bnz .Llderr -.Lw4end: - bas %r14,.Lwait4io - tm 8(%r5),0x82 # do we have a problem ? - bnz .Lrecov - slr %r7,%r7 - icm %r7,3,10(%r5) # get residual count - lcr %r7,%r7 - la %r7,IPL_BS(%r7) # IPL_BS-residual=#bytes read - ar %r2,%r7 # add to total size - tm 8(%r5),0x01 # found a tape mark ? - bnz .Ldone - l %r0,.Lccwread+4 # update CCW data addresses - ar %r0,%r7 - st %r0,.Lccwread+4 - b .Lldlp -.Ldone: - l %r14,.Lldret - br %r14 # r2 contains the total size -.Lrecov: - bas %r14,.Lsense # do the sensing - bct %r6,.Lssch # dec. retry count & branch - b .Llderr -# -# Sense subroutine -# -.Lsense: - st %r14,.Lsnsret - la %r7,.Lorbsense - ssch 0(%r7) # start sense command - bnz .Llderr - bas %r14,.Lwait4io - l %r14,.Lsnsret - tm 8(%r5),0x82 # do we have a problem ? - bnz .Llderr - br %r14 -# -# Wait for interrupt subroutine -# -.Lwait4io: - lpsw .Lwaitpsw -.Lioint: - c %r1,0xb8 # compare subchannel number - bne .Lwait4io - tsch 0(%r5) - slr %r0,%r0 - tm 8(%r5),0x82 # do we have a problem ? - bnz .Lwtexit - tm 8(%r5),0x04 # got device end ? - bz .Lwait4io -.Lwtexit: - br %r14 -.Llderr: - lpsw .Lcrash - - .align 8 -.Lorbread: - .long 0x00000000,0x0080ff00,.Lccwread - .align 8 -.Lorbsense: - .long 0x00000000,0x0080ff00,.Lccwsense - .align 8 -.Lccwread: - .long 0x02200000+IPL_BS,0x00000000 -.Lccwsense: - .long 0x04200001,0x00000000 -.Lwaitpsw: - .long 0x020a0000,0x80000000+.Lioint - -.Lirb: .long 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 -.Lcr6: .long 0xff000000 - .align 8 -.Lcrash:.long 0x000a0000,0x00000000 -.Lldret:.long 0 -.Lsnsret: .long 0 -#endif /* CONFIG_IPL_TAPE */ - -#ifdef CONFIG_IPL_VM -#define IPL_BS 0x730 - .org 0 - .long 0x00080000,0x80000000+iplstart # The first 24 bytes are loaded - .long 0x02000018,0x60000050 # by ipl to addresses 0-23. - .long 0x02000068,0x60000050 # (a PSW and two CCWs). - .fill 80-24,1,0x40 # bytes 24-79 are discarded !! - .long 0x020000f0,0x60000050 # The next 160 byte are loaded - .long 0x02000140,0x60000050 # to addresses 0x18-0xb7 - .long 0x02000190,0x60000050 # They form the continuation - .long 0x020001e0,0x60000050 # of the CCW program started - .long 0x02000230,0x60000050 # by ipl and load the range - .long 0x02000280,0x60000050 # 0x0f0-0x730 from the image - .long 0x020002d0,0x60000050 # to the range 0x0f0-0x730 - .long 0x02000320,0x60000050 # in memory. At the end of - .long 0x02000370,0x60000050 # the channel program the PSW - .long 0x020003c0,0x60000050 # at location 0 is loaded. - .long 0x02000410,0x60000050 # Initial processing starts - .long 0x02000460,0x60000050 # at 0xf0 = iplstart. - .long 0x020004b0,0x60000050 - .long 0x02000500,0x60000050 - .long 0x02000550,0x60000050 - .long 0x020005a0,0x60000050 - .long 0x020005f0,0x60000050 - .long 0x02000640,0x60000050 - .long 0x02000690,0x60000050 - .long 0x020006e0,0x20000050 - - .org 0xf0 -# -# subroutine for loading cards from the reader -# -.Lloader: - la %r3,.Lorb # r2 = address of orb into r2 - la %r5,.Lirb # r4 = address of irb - la %r6,.Lccws - la %r7,20 -.Linit: - st %r2,4(%r6) # initialize CCW data addresses - la %r2,0x50(%r2) - la %r6,8(%r6) - bct 7,.Linit - - lctl %c6,%c6,.Lcr6 # set IO subclass mask - slr %r2,%r2 -.Lldlp: - ssch 0(%r3) # load chunk of 1600 bytes - bnz .Llderr -.Lwait4irq: - mvc 0x78(8),.Lnewpsw # set up IO interrupt psw - lpsw .Lwaitpsw -.Lioint: - c %r1,0xb8 # compare subchannel number - bne .Lwait4irq - tsch 0(%r5) - - slr %r0,%r0 - ic %r0,8(%r5) # get device status - chi %r0,8 # channel end ? - be .Lcont - chi %r0,12 # channel end + device end ? - be .Lcont - - l %r0,4(%r5) - s %r0,8(%r3) # r0/8 = number of ccws executed - mhi %r0,10 # *10 = number of bytes in ccws - lh %r3,10(%r5) # get residual count - sr %r0,%r3 # #ccws*80-residual=#bytes read - ar %r2,%r0 - - br %r14 # r2 contains the total size - -.Lcont: - ahi %r2,0x640 # add 0x640 to total size - la %r6,.Lccws - la %r7,20 -.Lincr: - l %r0,4(%r6) # update CCW data addresses - ahi %r0,0x640 - st %r0,4(%r6) - ahi %r6,8 - bct 7,.Lincr - - b .Lldlp -.Llderr: - lpsw .Lcrash - - .align 8 -.Lorb: .long 0x00000000,0x0080ff00,.Lccws -.Lirb: .long 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 -.Lcr6: .long 0xff000000 -.Lloadp:.long 0,0 - .align 8 -.Lcrash:.long 0x000a0000,0x00000000 -.Lnewpsw: - .long 0x00080000,0x80000000+.Lioint -.Lwaitpsw: - .long 0x020a0000,0x80000000+.Lioint - - .align 8 -.Lccws: .rept 19 - .long 0x02600050,0x00000000 - .endr - .long 0x02200050,0x00000000 -#endif /* CONFIG_IPL_VM */ - -iplstart: - lh %r1,0xb8 # test if subchannel number - bct %r1,.Lnoload # is valid - l %r1,0xb8 # load ipl subchannel number - la %r2,IPL_BS # load start address - bas %r14,.Lloader # load rest of ipl image - l %r12,.Lparm # pointer to parameter area - st %r1,IPL_DEVICE+ARCH_OFFSET-PARMAREA(%r12) # save ipl device number - -# -# load parameter file from ipl device -# -.Lagain1: - l %r2,.Linitrd # ramdisk loc. is temp - bas %r14,.Lloader # load parameter file - ltr %r2,%r2 # got anything ? - bz .Lnopf - chi %r2,895 - bnh .Lnotrunc - la %r2,895 -.Lnotrunc: - l %r4,.Linitrd - clc 0(3,%r4),.L_hdr # if it is HDRx - bz .Lagain1 # skip dataset header - clc 0(3,%r4),.L_eof # if it is EOFx - bz .Lagain1 # skip dateset trailer - la %r5,0(%r4,%r2) - lr %r3,%r2 - la %r3,COMMAND_LINE-PARMAREA(%r12) # load adr. of command line - mvc 0(256,%r3),0(%r4) - mvc 256(256,%r3),256(%r4) - mvc 512(256,%r3),512(%r4) - mvc 768(122,%r3),768(%r4) - slr %r0,%r0 - b .Lcntlp -.Ldelspc: - ic %r0,0(%r2,%r3) - chi %r0,0x20 # is it a space ? - be .Lcntlp - ahi %r2,1 - b .Leolp -.Lcntlp: - brct %r2,.Ldelspc -.Leolp: - slr %r0,%r0 - stc %r0,0(%r2,%r3) # terminate buffer -.Lnopf: - -# -# load ramdisk from ipl device -# -.Lagain2: - l %r2,.Linitrd # addr of ramdisk - st %r2,INITRD_START+ARCH_OFFSET-PARMAREA(%r12) - bas %r14,.Lloader # load ramdisk - st %r2,INITRD_SIZE+ARCH_OFFSET-PARMAREA(%r12) # store size of rd - ltr %r2,%r2 - bnz .Lrdcont - st %r2,INITRD_START+ARCH_OFFSET-PARMAREA(%r12) # no ramdisk found -.Lrdcont: - l %r2,.Linitrd - - clc 0(3,%r2),.L_hdr # skip HDRx and EOFx - bz .Lagain2 - clc 0(3,%r2),.L_eof - bz .Lagain2 - -#ifdef CONFIG_IPL_VM -# -# reset files in VM reader -# - stidp __LC_SAVE_AREA_SYNC # store cpuid - tm __LC_SAVE_AREA_SYNC,0xff# running VM ? - bno .Lnoreset - la %r2,.Lreset - lhi %r3,26 - diag %r2,%r3,8 - la %r5,.Lirb - stsch 0(%r5) # check if irq is pending - tm 30(%r5),0x0f # by verifying if any of the - bnz .Lwaitforirq # activity or status control - tm 31(%r5),0xff # bits is set in the schib - bz .Lnoreset -.Lwaitforirq: - mvc 0x78(8),.Lrdrnewpsw # set up IO interrupt psw -.Lwaitrdrirq: - lpsw .Lrdrwaitpsw -.Lrdrint: - c %r1,0xb8 # compare subchannel number - bne .Lwaitrdrirq - la %r5,.Lirb - tsch 0(%r5) -.Lnoreset: - b .Lnoload - - .align 8 -.Lrdrnewpsw: - .long 0x00080000,0x80000000+.Lrdrint -.Lrdrwaitpsw: - .long 0x020a0000,0x80000000+.Lrdrint -#endif - -# -# everything loaded, go for it -# -.Lnoload: - l %r1,.Lstartup - br %r1 - -.Linitrd:.long _end # default address of initrd -.Lparm: .long PARMAREA -.Lstartup: .long startup -.Lreset:.byte 0xc3,0xc8,0xc1,0xd5,0xc7,0xc5,0x40,0xd9,0xc4,0xd9,0x40 - .byte 0xc1,0xd3,0xd3,0x40,0xd2,0xc5,0xc5,0xd7,0x40,0xd5,0xd6 - .byte 0xc8,0xd6,0xd3,0xc4 # "change rdr all keep nohold" -.L_eof: .long 0xc5d6c600 /* C'EOF' */ -.L_hdr: .long 0xc8c4d900 /* C'HDR' */ - -#endif /* CONFIG_IPL */ - -# -# SALIPL loader support. Based on a patch by Rob van der Heij. -# This entry point is called directly from the SALIPL loader and -# doesn't need a builtin ipl record. -# - .org 0x800 -ENTRY(start) - stm %r0,%r15,0x07b0 # store registers - basr %r12,%r0 -.base: - l %r11,.parm - l %r8,.cmd # pointer to command buffer - - ltr %r9,%r9 # do we have SALIPL parameters? - bp .sk8x8 - - mvc 0(64,%r8),0x00b0 # copy saved registers - xc 64(240-64,%r8),0(%r8) # remainder of buffer - tr 0(64,%r8),.lowcase - b .gotr -.sk8x8: - mvc 0(240,%r8),0(%r9) # copy iplparms into buffer -.gotr: - slr %r0,%r0 - st %r0,INITRD_SIZE+ARCH_OFFSET-PARMAREA(%r11) - st %r0,INITRD_START+ARCH_OFFSET-PARMAREA(%r11) - j startup # continue with startup -.cmd: .long COMMAND_LINE # address of command line buffer -.parm: .long PARMAREA -.lowcase: - .byte 0x00,0x01,0x02,0x03,0x04,0x05,0x06,0x07 - .byte 0x08,0x09,0x0a,0x0b,0x0c,0x0d,0x0e,0x0f - .byte 0x10,0x11,0x12,0x13,0x14,0x15,0x16,0x17 - .byte 0x18,0x19,0x1a,0x1b,0x1c,0x1d,0x1e,0x1f - .byte 0x20,0x21,0x22,0x23,0x24,0x25,0x26,0x27 - .byte 0x28,0x29,0x2a,0x2b,0x2c,0x2d,0x2e,0x2f - .byte 0x30,0x31,0x32,0x33,0x34,0x35,0x36,0x37 - .byte 0x38,0x39,0x3a,0x3b,0x3c,0x3d,0x3e,0x3f - .byte 0x40,0x41,0x42,0x43,0x44,0x45,0x46,0x47 - .byte 0x48,0x49,0x4a,0x4b,0x4c,0x4d,0x4e,0x4f - .byte 0x50,0x51,0x52,0x53,0x54,0x55,0x56,0x57 - .byte 0x58,0x59,0x5a,0x5b,0x5c,0x5d,0x5e,0x5f - .byte 0x60,0x61,0x62,0x63,0x64,0x65,0x66,0x67 - .byte 0x68,0x69,0x6a,0x6b,0x6c,0x6d,0x6e,0x6f - .byte 0x70,0x71,0x72,0x73,0x74,0x75,0x76,0x77 - .byte 0x78,0x79,0x7a,0x7b,0x7c,0x7d,0x7e,0x7f - - .byte 0x80,0x81,0x82,0x83,0x84,0x85,0x86,0x87 - .byte 0x88,0x89,0x8a,0x8b,0x8c,0x8d,0x8e,0x8f - .byte 0x90,0x91,0x92,0x93,0x94,0x95,0x96,0x97 - .byte 0x98,0x99,0x9a,0x9b,0x9c,0x9d,0x9e,0x9f - .byte 0xa0,0xa1,0xa2,0xa3,0xa4,0xa5,0xa6,0xa7 - .byte 0xa8,0xa9,0xaa,0xab,0xac,0xad,0xae,0xaf - .byte 0xb0,0xb1,0xb2,0xb3,0xb4,0xb5,0xb6,0xb7 - .byte 0xb8,0xb9,0xba,0xbb,0xbc,0xbd,0xbe,0xbf - .byte 0xc0,0x81,0x82,0x83,0x84,0x85,0x86,0x87 # .abcdefg - .byte 0x88,0x89,0xca,0xcb,0xcc,0xcd,0xce,0xcf # hi - .byte 0xd0,0x91,0x92,0x93,0x94,0x95,0x96,0x97 # .jklmnop - .byte 0x98,0x99,0xda,0xdb,0xdc,0xdd,0xde,0xdf # qr - .byte 0xe0,0xe1,0xa2,0xa3,0xa4,0xa5,0xa6,0xa7 # ..stuvwx - .byte 0xa8,0xa9,0xea,0xeb,0xec,0xed,0xee,0xef # yz - .byte 0xf0,0xf1,0xf2,0xf3,0xf4,0xf5,0xf6,0xf7 - .byte 0xf8,0xf9,0xfa,0xfb,0xfc,0xfd,0xfe,0xff - -# -# startup-code at 0x10000, running in absolute addressing mode -# this is called either by the ipl loader or directly by PSW restart -# or linload or SALIPL -# - .org 0x10000 -ENTRY(startup) - j .Lep_startup_normal - .org 0x10008 -# -# This is a list of s390 kernel entry points. At address 0x1000f the number of -# valid entry points is stored. -# -# IMPORTANT: Do not change this table, it is s390 kernel ABI! -# - .ascii "S390EP" - .byte 0x00,0x01 -# -# kdump startup-code at 0x10010, running in 64 bit absolute addressing mode -# - .org 0x10010 -ENTRY(startup_kdump) - j .Lep_startup_kdump -.Lep_startup_normal: - basr %r13,0 # get base -.LPG0: - xc 0x200(256),0x200 # partially clear lowcore - xc 0x300(256),0x300 - xc 0xe00(256),0xe00 - stck __LC_LAST_UPDATE_CLOCK - spt 5f-.LPG0(%r13) - mvc __LC_LAST_UPDATE_TIMER(8),5f-.LPG0(%r13) - xc __LC_STFL_FAC_LIST(8),__LC_STFL_FAC_LIST -#ifndef CONFIG_MARCH_G5 - # check capabilities against MARCH_{G5,Z900,Z990,Z9_109,Z10} - .insn s,0xb2b10000,__LC_STFL_FAC_LIST # store facility list - tm __LC_STFL_FAC_LIST,0x01 # stfle available ? - jz 0f - la %r0,0 - .insn s,0xb2b00000,__LC_STFL_FAC_LIST # store facility list extended -0: l %r0,__LC_STFL_FAC_LIST - n %r0,2f+8-.LPG0(%r13) - cl %r0,2f+8-.LPG0(%r13) - jne 1f - l %r0,__LC_STFL_FAC_LIST+4 - n %r0,2f+12-.LPG0(%r13) - cl %r0,2f+12-.LPG0(%r13) - je 3f -1: l %r15,.Lstack-.LPG0(%r13) - ahi %r15,-96 - la %r2,.Lals_string-.LPG0(%r13) - l %r3,.Lsclp_print-.LPG0(%r13) - basr %r14,%r3 - lpsw 2f-.LPG0(%r13) # machine type not good enough, crash -.Lals_string: - .asciz "The Linux kernel requires more recent processor hardware" -.Lsclp_print: - .long _sclp_print_early -.Lstack: - .long 0x8000 + (1<<(PAGE_SHIFT+THREAD_ORDER)) - .align 16 -2: .long 0x000a0000,0x8badcccc -#if defined(CONFIG_64BIT) -#if defined(CONFIG_MARCH_Z196) - .long 0xc100efe3, 0xf46c0000 -#elif defined(CONFIG_MARCH_Z10) - .long 0xc100efe3, 0xf0680000 -#elif defined(CONFIG_MARCH_Z9_109) - .long 0xc100efc3, 0x00000000 -#elif defined(CONFIG_MARCH_Z990) - .long 0xc0002000, 0x00000000 -#elif defined(CONFIG_MARCH_Z900) - .long 0xc0000000, 0x00000000 -#endif -#else -#if defined(CONFIG_MARCH_Z196) - .long 0x8100c880, 0x00000000 -#elif defined(CONFIG_MARCH_Z10) - .long 0x8100c880, 0x00000000 -#elif defined(CONFIG_MARCH_Z9_109) - .long 0x8100c880, 0x00000000 -#elif defined(CONFIG_MARCH_Z990) - .long 0x80002000, 0x00000000 -#elif defined(CONFIG_MARCH_Z900) - .long 0x80000000, 0x00000000 -#endif -#endif -3: -#endif - -#ifdef CONFIG_64BIT - mvi __LC_AR_MODE_ID,1 # set esame flag - slr %r0,%r0 # set cpuid to zero - lhi %r1,2 # mode 2 = esame (dump) - sigp %r1,%r0,0x12 # switch to esame mode - sam64 # switch to 64 bit mode - larl %r13,4f - lmh %r0,%r15,0(%r13) # clear high-order half - jg startup_continue -4: .fill 16,4,0x0 -#else - mvi __LC_AR_MODE_ID,0 # set ESA flag (mode 0) - l %r13,4f-.LPG0(%r13) - b 0(%r13) - .align 8 -4: .long startup_continue -#endif - .align 8 -5: .long 0x7fffffff,0xffffffff - -#include "head_kdump.S" - -# -# params at 10400 (setup.h) -# - .org PARMAREA - .long 0,0 # IPL_DEVICE - .long 0,0 # INITRD_START - .long 0,0 # INITRD_SIZE - .long 0,0 # OLDMEM_BASE - .long 0,0 # OLDMEM_SIZE - - .org COMMAND_LINE - .byte "root=/dev/ram0 ro" - .byte 0 - - .org 0x11000 diff --git a/ANDROID_3.4.5/arch/s390/kernel/head31.S b/ANDROID_3.4.5/arch/s390/kernel/head31.S deleted file mode 100644 index d3f1ab7d..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/head31.S +++ /dev/null @@ -1,112 +0,0 @@ -/* - * arch/s390/kernel/head31.S - * - * Copyright (C) IBM Corp. 2005,2010 - * - * Author(s): Hartmut Penner <hp@de.ibm.com> - * Martin Schwidefsky <schwidefsky@de.ibm.com> - * Rob van der Heij <rvdhei@iae.nl> - * Heiko Carstens <heiko.carstens@de.ibm.com> - * - */ - -#include <linux/init.h> -#include <linux/linkage.h> -#include <asm/asm-offsets.h> -#include <asm/thread_info.h> -#include <asm/page.h> - -__HEAD -ENTRY(startup_continue) - basr %r13,0 # get base -.LPG1: - - l %r1,.Lbase_cc-.LPG1(%r13) - mvc 0(8,%r1),__LC_LAST_UPDATE_CLOCK - lctl %c0,%c15,.Lctl-.LPG1(%r13) # load control registers - l %r12,.Lparmaddr-.LPG1(%r13) # pointer to parameter area - # move IPL device to lowcore -# -# Setup stack -# - l %r15,.Linittu-.LPG1(%r13) - st %r15,__LC_THREAD_INFO # cache thread info in lowcore - mvc __LC_CURRENT(4),__TI_task(%r15) - ahi %r15,1<<(PAGE_SHIFT+THREAD_ORDER) # init_task_union+THREAD_SIZE - st %r15,__LC_KERNEL_STACK # set end of kernel stack - ahi %r15,-96 -# -# Save ipl parameters, clear bss memory, initialize storage key for kernel pages, -# and create a kernel NSS if the SAVESYS= parm is defined -# - l %r14,.Lstartup_init-.LPG1(%r13) - basr %r14,%r14 - lpsw .Lentry-.LPG1(13) # jump to _stext in primary-space, - # virtual and never return ... - .align 8 -.Lentry:.long 0x00080000,0x80000000 + _stext -.Lctl: .long 0x04b50000 # cr0: various things - .long 0 # cr1: primary space segment table - .long .Lduct # cr2: dispatchable unit control table - .long 0 # cr3: instruction authorization - .long 0 # cr4: instruction authorization - .long .Lduct # cr5: primary-aste origin - .long 0 # cr6: I/O interrupts - .long 0 # cr7: secondary space segment table - .long 0 # cr8: access registers translation - .long 0 # cr9: tracing off - .long 0 # cr10: tracing off - .long 0 # cr11: tracing off - .long 0 # cr12: tracing off - .long 0 # cr13: home space segment table - .long 0xc0000000 # cr14: machine check handling off - .long 0 # cr15: linkage stack operations -.Lmchunk:.long memory_chunk -.Lbss_bgn: .long __bss_start -.Lbss_end: .long _end -.Lparmaddr: .long PARMAREA -.Linittu: .long init_thread_union -.Lstartup_init: - .long startup_init - .align 64 -.Lduct: .long 0,0,0,0,.Lduald,0,0,0 - .long 0,0,0,0,0,0,0,0 - .align 128 -.Lduald:.rept 8 - .long 0x80000000,0,0,0 # invalid access-list entries - .endr -.Lbase_cc: - .long sched_clock_base_cc - -ENTRY(_ehead) - -#ifdef CONFIG_SHARED_KERNEL - .org 0x100000 - 0x11000 # head.o ends at 0x11000 -#endif - -# -# startup-code, running in absolute addressing mode -# -ENTRY(_stext) - basr %r13,0 # get base -.LPG3: -# check control registers - stctl %c0,%c15,0(%r15) - oi 2(%r15),0x60 # enable sigp emergency & external call - oi 0(%r15),0x10 # switch on low address protection - lctl %c0,%c15,0(%r15) - -# - lam 0,15,.Laregs-.LPG3(%r13) # load access regs needed by uaccess - l %r14,.Lstart-.LPG3(%r13) - basr %r14,%r14 # call start_kernel -# -# We returned from start_kernel ?!? PANIK -# - basr %r13,0 - lpsw .Ldw-.(%r13) # load disabled wait psw -# - .align 8 -.Ldw: .long 0x000a0000,0x00000000 -.Lstart:.long start_kernel -.Laregs:.long 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 diff --git a/ANDROID_3.4.5/arch/s390/kernel/head64.S b/ANDROID_3.4.5/arch/s390/kernel/head64.S deleted file mode 100644 index 99348c0e..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/head64.S +++ /dev/null @@ -1,107 +0,0 @@ -/* - * arch/s390/kernel/head64.S - * - * Copyright (C) IBM Corp. 1999,2010 - * - * Author(s): Hartmut Penner <hp@de.ibm.com> - * Martin Schwidefsky <schwidefsky@de.ibm.com> - * Rob van der Heij <rvdhei@iae.nl> - * Heiko Carstens <heiko.carstens@de.ibm.com> - * - */ - -#include <linux/init.h> -#include <linux/linkage.h> -#include <asm/asm-offsets.h> -#include <asm/thread_info.h> -#include <asm/page.h> - -__HEAD -ENTRY(startup_continue) - larl %r1,sched_clock_base_cc - mvc 0(8,%r1),__LC_LAST_UPDATE_CLOCK - larl %r13,.LPG1 # get base - lctlg %c0,%c15,.Lctl-.LPG1(%r13) # load control registers - lg %r12,.Lparmaddr-.LPG1(%r13) # pointer to parameter area - # move IPL device to lowcore - lghi %r0,__LC_PASTE - stg %r0,__LC_VDSO_PER_CPU -# -# Setup stack -# - larl %r15,init_thread_union - stg %r15,__LC_THREAD_INFO # cache thread info in lowcore - lg %r14,__TI_task(%r15) # cache current in lowcore - stg %r14,__LC_CURRENT - aghi %r15,1<<(PAGE_SHIFT+THREAD_ORDER) # init_task_union + THREAD_SIZE - stg %r15,__LC_KERNEL_STACK # set end of kernel stack - aghi %r15,-160 -# -# Save ipl parameters, clear bss memory, initialize storage key for kernel pages, -# and create a kernel NSS if the SAVESYS= parm is defined -# - brasl %r14,startup_init - lpswe .Lentry-.LPG1(13) # jump to _stext in primary-space, - # virtual and never return ... - .align 16 -.LPG1: -.Lentry:.quad 0x0000000180000000,_stext -.Lctl: .quad 0x04040000 # cr0: AFP registers & secondary space - .quad 0 # cr1: primary space segment table - .quad .Lduct # cr2: dispatchable unit control table - .quad 0 # cr3: instruction authorization - .quad 0 # cr4: instruction authorization - .quad .Lduct # cr5: primary-aste origin - .quad 0 # cr6: I/O interrupts - .quad 0 # cr7: secondary space segment table - .quad 0 # cr8: access registers translation - .quad 0 # cr9: tracing off - .quad 0 # cr10: tracing off - .quad 0 # cr11: tracing off - .quad 0 # cr12: tracing off - .quad 0 # cr13: home space segment table - .quad 0xc0000000 # cr14: machine check handling off - .quad 0 # cr15: linkage stack operations -.Lpcmsk:.quad 0x0000000180000000 -.L4malign:.quad 0xffffffffffc00000 -.Lscan2g:.quad 0x80000000 + 0x20000 - 8 # 2GB + 128K - 8 -.Lnop: .long 0x07000700 -.Lparmaddr: - .quad PARMAREA - .align 64 -.Lduct: .long 0,0,0,0,.Lduald,0,0,0 - .long 0,0,0,0,0,0,0,0 - .align 128 -.Lduald:.rept 8 - .long 0x80000000,0,0,0 # invalid access-list entries - .endr - -ENTRY(_ehead) - -#ifdef CONFIG_SHARED_KERNEL - .org 0x100000 - 0x11000 # head.o ends at 0x11000 -#endif - -# -# startup-code, running in absolute addressing mode -# -ENTRY(_stext) - basr %r13,0 # get base -.LPG3: -# check control registers - stctg %c0,%c15,0(%r15) - oi 6(%r15),0x60 # enable sigp emergency & external call - oi 4(%r15),0x10 # switch on low address proctection - lctlg %c0,%c15,0(%r15) - - lam 0,15,.Laregs-.LPG3(%r13) # load acrs needed by uaccess - brasl %r14,start_kernel # go to C code -# -# We returned from start_kernel ?!? PANIK -# - basr %r13,0 - lpswe .Ldw-.(%r13) # load disabled wait psw - - .align 8 -.Ldw: .quad 0x0002000180000000,0x0000000000000000 -.Laregs:.long 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 diff --git a/ANDROID_3.4.5/arch/s390/kernel/head_kdump.S b/ANDROID_3.4.5/arch/s390/kernel/head_kdump.S deleted file mode 100644 index e1ac3893..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/head_kdump.S +++ /dev/null @@ -1,119 +0,0 @@ -/* - * S390 kdump lowlevel functions (new kernel) - * - * Copyright IBM Corp. 2011 - * Author(s): Michael Holzheu <holzheu@linux.vnet.ibm.com> - */ - -#define DATAMOVER_ADDR 0x4000 -#define COPY_PAGE_ADDR 0x6000 - -#ifdef CONFIG_CRASH_DUMP - -# -# kdump entry (new kernel - not yet relocated) -# -# Note: This code has to be position independent -# - -.align 2 -.Lep_startup_kdump: - lhi %r1,2 # mode 2 = esame (dump) - sigp %r1,%r0,0x12 # Switch to esame mode - sam64 # Switch to 64 bit addressing - basr %r13,0 -.Lbase: - larl %r2,.Lbase_addr # Check, if we have been - lg %r2,0(%r2) # already relocated: - clgr %r2,%r13 # - jne .Lrelocate # No : Start data mover - lghi %r2,0 # Yes: Start kdump kernel - brasl %r14,startup_kdump_relocated - -.Lrelocate: - larl %r4,startup - lg %r2,0x418(%r4) # Get kdump base - lg %r3,0x420(%r4) # Get kdump size - - larl %r10,.Lcopy_start # Source of data mover - lghi %r8,DATAMOVER_ADDR # Target of data mover - mvc 0(256,%r8),0(%r10) # Copy data mover code - - agr %r8,%r2 # Copy data mover to - mvc 0(256,%r8),0(%r10) # reserved mem - - lghi %r14,DATAMOVER_ADDR # Jump to copied data mover - basr %r14,%r14 -.Lbase_addr: - .quad .Lbase - -# -# kdump data mover code (runs at address DATAMOVER_ADDR) -# -# r2: kdump base address -# r3: kdump size -# -.Lcopy_start: - basr %r13,0 # Base -0: - lgr %r11,%r2 # Save kdump base address - lgr %r12,%r2 - agr %r12,%r3 # Compute kdump end address - - lghi %r5,0 - lghi %r10,COPY_PAGE_ADDR # Load copy page address -1: - mvc 0(256,%r10),0(%r5) # Copy old kernel to tmp - mvc 0(256,%r5),0(%r11) # Copy new kernel to old - mvc 0(256,%r11),0(%r10) # Copy tmp to new - aghi %r11,256 - aghi %r5,256 - clgr %r11,%r12 - jl 1b - - lg %r14,.Lstartup_kdump-0b(%r13) - basr %r14,%r14 # Start relocated kernel -.Lstartup_kdump: - .long 0x00000000,0x00000000 + startup_kdump_relocated -.Lcopy_end: - -# -# Startup of kdump (relocated new kernel) -# -.align 2 -startup_kdump_relocated: - basr %r13,0 -0: - mvc 0(8,%r0),.Lrestart_psw-0b(%r13) # Setup restart PSW - mvc 464(16,%r0),.Lpgm_psw-0b(%r13) # Setup pgm check PSW - lhi %r1,1 # Start new kernel - diag %r1,%r1,0x308 # with diag 308 - -.Lno_diag308: # No diag 308 - sam31 # Switch to 31 bit addr mode - sr %r1,%r1 # Erase register r1 - sr %r2,%r2 # Erase register r2 - sigp %r1,%r2,0x12 # Switch to 31 bit arch mode - lpsw 0 # Start new kernel... -.align 8 -.Lrestart_psw: - .long 0x00080000,0x80000000 + startup -.Lpgm_psw: - .quad 0x0000000180000000,0x0000000000000000 + .Lno_diag308 -#else -.align 2 -.Lep_startup_kdump: -#ifdef CONFIG_64BIT - larl %r13,startup_kdump_crash - lpswe 0(%r13) -.align 8 -startup_kdump_crash: - .quad 0x0002000080000000,0x0000000000000000 + startup_kdump_crash -#else - basr %r13,0 -0: lpsw startup_kdump_crash-0b(%r13) -.align 8 -startup_kdump_crash: - .long 0x000a0000,0x00000000 + startup_kdump_crash -#endif /* CONFIG_64BIT */ -#endif /* CONFIG_CRASH_DUMP */ diff --git a/ANDROID_3.4.5/arch/s390/kernel/init_task.c b/ANDROID_3.4.5/arch/s390/kernel/init_task.c deleted file mode 100644 index 4d1c9fb0..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/init_task.c +++ /dev/null @@ -1,38 +0,0 @@ -/* - * arch/s390/kernel/init_task.c - * - * S390 version - * - * Derived from "arch/i386/kernel/init_task.c" - */ - -#include <linux/mm.h> -#include <linux/fs.h> -#include <linux/module.h> -#include <linux/sched.h> -#include <linux/init_task.h> -#include <linux/mqueue.h> - -#include <asm/uaccess.h> -#include <asm/pgtable.h> - -static struct signal_struct init_signals = INIT_SIGNALS(init_signals); -static struct sighand_struct init_sighand = INIT_SIGHAND(init_sighand); -/* - * Initial thread structure. - * - * We need to make sure that this is THREAD_SIZE aligned due to the - * way process stacks are handled. This is done by having a special - * "init_task" linker map entry.. - */ -union thread_union init_thread_union __init_task_data = - { INIT_THREAD_INFO(init_task) }; - -/* - * Initial task structure. - * - * All other task structs will be allocated on slabs in fork.c - */ -struct task_struct init_task = INIT_TASK(init_task); - -EXPORT_SYMBOL(init_task); diff --git a/ANDROID_3.4.5/arch/s390/kernel/ipl.c b/ANDROID_3.4.5/arch/s390/kernel/ipl.c deleted file mode 100644 index 8342e65a..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/ipl.c +++ /dev/null @@ -1,2069 +0,0 @@ -/* - * arch/s390/kernel/ipl.c - * ipl/reipl/dump support for Linux on s390. - * - * Copyright IBM Corp. 2005,2012 - * Author(s): Michael Holzheu <holzheu@de.ibm.com> - * Heiko Carstens <heiko.carstens@de.ibm.com> - * Volker Sameske <sameske@de.ibm.com> - */ - -#include <linux/types.h> -#include <linux/module.h> -#include <linux/device.h> -#include <linux/delay.h> -#include <linux/reboot.h> -#include <linux/ctype.h> -#include <linux/fs.h> -#include <linux/gfp.h> -#include <linux/crash_dump.h> -#include <linux/debug_locks.h> -#include <asm/ipl.h> -#include <asm/smp.h> -#include <asm/setup.h> -#include <asm/cpcmd.h> -#include <asm/cio.h> -#include <asm/ebcdic.h> -#include <asm/reset.h> -#include <asm/sclp.h> -#include <asm/checksum.h> -#include <asm/debug.h> -#include <asm/os_info.h> -#include "entry.h" - -#define IPL_PARM_BLOCK_VERSION 0 - -#define IPL_UNKNOWN_STR "unknown" -#define IPL_CCW_STR "ccw" -#define IPL_FCP_STR "fcp" -#define IPL_FCP_DUMP_STR "fcp_dump" -#define IPL_NSS_STR "nss" - -#define DUMP_CCW_STR "ccw" -#define DUMP_FCP_STR "fcp" -#define DUMP_NONE_STR "none" - -/* - * Four shutdown trigger types are supported: - * - panic - * - halt - * - power off - * - reipl - * - restart - */ -#define ON_PANIC_STR "on_panic" -#define ON_HALT_STR "on_halt" -#define ON_POFF_STR "on_poff" -#define ON_REIPL_STR "on_reboot" -#define ON_RESTART_STR "on_restart" - -struct shutdown_action; -struct shutdown_trigger { - char *name; - struct shutdown_action *action; -}; - -/* - * The following shutdown action types are supported: - */ -#define SHUTDOWN_ACTION_IPL_STR "ipl" -#define SHUTDOWN_ACTION_REIPL_STR "reipl" -#define SHUTDOWN_ACTION_DUMP_STR "dump" -#define SHUTDOWN_ACTION_VMCMD_STR "vmcmd" -#define SHUTDOWN_ACTION_STOP_STR "stop" -#define SHUTDOWN_ACTION_DUMP_REIPL_STR "dump_reipl" - -struct shutdown_action { - char *name; - void (*fn) (struct shutdown_trigger *trigger); - int (*init) (void); - int init_rc; -}; - -static char *ipl_type_str(enum ipl_type type) -{ - switch (type) { - case IPL_TYPE_CCW: - return IPL_CCW_STR; - case IPL_TYPE_FCP: - return IPL_FCP_STR; - case IPL_TYPE_FCP_DUMP: - return IPL_FCP_DUMP_STR; - case IPL_TYPE_NSS: - return IPL_NSS_STR; - case IPL_TYPE_UNKNOWN: - default: - return IPL_UNKNOWN_STR; - } -} - -enum dump_type { - DUMP_TYPE_NONE = 1, - DUMP_TYPE_CCW = 2, - DUMP_TYPE_FCP = 4, -}; - -static char *dump_type_str(enum dump_type type) -{ - switch (type) { - case DUMP_TYPE_NONE: - return DUMP_NONE_STR; - case DUMP_TYPE_CCW: - return DUMP_CCW_STR; - case DUMP_TYPE_FCP: - return DUMP_FCP_STR; - default: - return NULL; - } -} - -/* - * Must be in data section since the bss section - * is not cleared when these are accessed. - */ -static u16 ipl_devno __attribute__((__section__(".data"))) = 0; -u32 ipl_flags __attribute__((__section__(".data"))) = 0; - -enum ipl_method { - REIPL_METHOD_CCW_CIO, - REIPL_METHOD_CCW_DIAG, - REIPL_METHOD_CCW_VM, - REIPL_METHOD_FCP_RO_DIAG, - REIPL_METHOD_FCP_RW_DIAG, - REIPL_METHOD_FCP_RO_VM, - REIPL_METHOD_FCP_DUMP, - REIPL_METHOD_NSS, - REIPL_METHOD_NSS_DIAG, - REIPL_METHOD_DEFAULT, -}; - -enum dump_method { - DUMP_METHOD_NONE, - DUMP_METHOD_CCW_CIO, - DUMP_METHOD_CCW_DIAG, - DUMP_METHOD_CCW_VM, - DUMP_METHOD_FCP_DIAG, -}; - -static int diag308_set_works = 0; - -static struct ipl_parameter_block ipl_block; - -static int reipl_capabilities = IPL_TYPE_UNKNOWN; - -static enum ipl_type reipl_type = IPL_TYPE_UNKNOWN; -static enum ipl_method reipl_method = REIPL_METHOD_DEFAULT; -static struct ipl_parameter_block *reipl_block_fcp; -static struct ipl_parameter_block *reipl_block_ccw; -static struct ipl_parameter_block *reipl_block_nss; -static struct ipl_parameter_block *reipl_block_actual; - -static int dump_capabilities = DUMP_TYPE_NONE; -static enum dump_type dump_type = DUMP_TYPE_NONE; -static enum dump_method dump_method = DUMP_METHOD_NONE; -static struct ipl_parameter_block *dump_block_fcp; -static struct ipl_parameter_block *dump_block_ccw; - -static struct sclp_ipl_info sclp_ipl_info; - -int diag308(unsigned long subcode, void *addr) -{ - register unsigned long _addr asm("0") = (unsigned long) addr; - register unsigned long _rc asm("1") = 0; - - asm volatile( - " diag %0,%2,0x308\n" - "0:\n" - EX_TABLE(0b,0b) - : "+d" (_addr), "+d" (_rc) - : "d" (subcode) : "cc", "memory"); - return _rc; -} -EXPORT_SYMBOL_GPL(diag308); - -/* SYSFS */ - -#define DEFINE_IPL_ATTR_RO(_prefix, _name, _format, _value) \ -static ssize_t sys_##_prefix##_##_name##_show(struct kobject *kobj, \ - struct kobj_attribute *attr, \ - char *page) \ -{ \ - return sprintf(page, _format, _value); \ -} \ -static struct kobj_attribute sys_##_prefix##_##_name##_attr = \ - __ATTR(_name, S_IRUGO, sys_##_prefix##_##_name##_show, NULL); - -#define DEFINE_IPL_ATTR_RW(_prefix, _name, _fmt_out, _fmt_in, _value) \ -static ssize_t sys_##_prefix##_##_name##_show(struct kobject *kobj, \ - struct kobj_attribute *attr, \ - char *page) \ -{ \ - return sprintf(page, _fmt_out, \ - (unsigned long long) _value); \ -} \ -static ssize_t sys_##_prefix##_##_name##_store(struct kobject *kobj, \ - struct kobj_attribute *attr, \ - const char *buf, size_t len) \ -{ \ - unsigned long long value; \ - if (sscanf(buf, _fmt_in, &value) != 1) \ - return -EINVAL; \ - _value = value; \ - return len; \ -} \ -static struct kobj_attribute sys_##_prefix##_##_name##_attr = \ - __ATTR(_name,(S_IRUGO | S_IWUSR), \ - sys_##_prefix##_##_name##_show, \ - sys_##_prefix##_##_name##_store); - -#define DEFINE_IPL_ATTR_STR_RW(_prefix, _name, _fmt_out, _fmt_in, _value)\ -static ssize_t sys_##_prefix##_##_name##_show(struct kobject *kobj, \ - struct kobj_attribute *attr, \ - char *page) \ -{ \ - return sprintf(page, _fmt_out, _value); \ -} \ -static ssize_t sys_##_prefix##_##_name##_store(struct kobject *kobj, \ - struct kobj_attribute *attr, \ - const char *buf, size_t len) \ -{ \ - strncpy(_value, buf, sizeof(_value) - 1); \ - strim(_value); \ - return len; \ -} \ -static struct kobj_attribute sys_##_prefix##_##_name##_attr = \ - __ATTR(_name,(S_IRUGO | S_IWUSR), \ - sys_##_prefix##_##_name##_show, \ - sys_##_prefix##_##_name##_store); - -static void make_attrs_ro(struct attribute **attrs) -{ - while (*attrs) { - (*attrs)->mode = S_IRUGO; - attrs++; - } -} - -/* - * ipl section - */ - -static __init enum ipl_type get_ipl_type(void) -{ - struct ipl_parameter_block *ipl = IPL_PARMBLOCK_START; - - if (ipl_flags & IPL_NSS_VALID) - return IPL_TYPE_NSS; - if (!(ipl_flags & IPL_DEVNO_VALID)) - return IPL_TYPE_UNKNOWN; - if (!(ipl_flags & IPL_PARMBLOCK_VALID)) - return IPL_TYPE_CCW; - if (ipl->hdr.version > IPL_MAX_SUPPORTED_VERSION) - return IPL_TYPE_UNKNOWN; - if (ipl->hdr.pbt != DIAG308_IPL_TYPE_FCP) - return IPL_TYPE_UNKNOWN; - if (ipl->ipl_info.fcp.opt == DIAG308_IPL_OPT_DUMP) - return IPL_TYPE_FCP_DUMP; - return IPL_TYPE_FCP; -} - -struct ipl_info ipl_info; -EXPORT_SYMBOL_GPL(ipl_info); - -static ssize_t ipl_type_show(struct kobject *kobj, struct kobj_attribute *attr, - char *page) -{ - return sprintf(page, "%s\n", ipl_type_str(ipl_info.type)); -} - -static struct kobj_attribute sys_ipl_type_attr = __ATTR_RO(ipl_type); - -/* VM IPL PARM routines */ -static size_t reipl_get_ascii_vmparm(char *dest, size_t size, - const struct ipl_parameter_block *ipb) -{ - int i; - size_t len; - char has_lowercase = 0; - - len = 0; - if ((ipb->ipl_info.ccw.vm_flags & DIAG308_VM_FLAGS_VP_VALID) && - (ipb->ipl_info.ccw.vm_parm_len > 0)) { - - len = min_t(size_t, size - 1, ipb->ipl_info.ccw.vm_parm_len); - memcpy(dest, ipb->ipl_info.ccw.vm_parm, len); - /* If at least one character is lowercase, we assume mixed - * case; otherwise we convert everything to lowercase. - */ - for (i = 0; i < len; i++) - if ((dest[i] > 0x80 && dest[i] < 0x8a) || /* a-i */ - (dest[i] > 0x90 && dest[i] < 0x9a) || /* j-r */ - (dest[i] > 0xa1 && dest[i] < 0xaa)) { /* s-z */ - has_lowercase = 1; - break; - } - if (!has_lowercase) - EBC_TOLOWER(dest, len); - EBCASC(dest, len); - } - dest[len] = 0; - - return len; -} - -size_t append_ipl_vmparm(char *dest, size_t size) -{ - size_t rc; - - rc = 0; - if (diag308_set_works && (ipl_block.hdr.pbt == DIAG308_IPL_TYPE_CCW)) - rc = reipl_get_ascii_vmparm(dest, size, &ipl_block); - else - dest[0] = 0; - return rc; -} - -static ssize_t ipl_vm_parm_show(struct kobject *kobj, - struct kobj_attribute *attr, char *page) -{ - char parm[DIAG308_VMPARM_SIZE + 1] = {}; - - append_ipl_vmparm(parm, sizeof(parm)); - return sprintf(page, "%s\n", parm); -} - -static size_t scpdata_length(const char* buf, size_t count) -{ - while (count) { - if (buf[count - 1] != '\0' && buf[count - 1] != ' ') - break; - count--; - } - return count; -} - -static size_t reipl_append_ascii_scpdata(char *dest, size_t size, - const struct ipl_parameter_block *ipb) -{ - size_t count; - size_t i; - int has_lowercase; - - count = min(size - 1, scpdata_length(ipb->ipl_info.fcp.scp_data, - ipb->ipl_info.fcp.scp_data_len)); - if (!count) - goto out; - - has_lowercase = 0; - for (i = 0; i < count; i++) { - if (!isascii(ipb->ipl_info.fcp.scp_data[i])) { - count = 0; - goto out; - } - if (!has_lowercase && islower(ipb->ipl_info.fcp.scp_data[i])) - has_lowercase = 1; - } - - if (has_lowercase) - memcpy(dest, ipb->ipl_info.fcp.scp_data, count); - else - for (i = 0; i < count; i++) - dest[i] = tolower(ipb->ipl_info.fcp.scp_data[i]); -out: - dest[count] = '\0'; - return count; -} - -size_t append_ipl_scpdata(char *dest, size_t len) -{ - size_t rc; - - rc = 0; - if (ipl_block.hdr.pbt == DIAG308_IPL_TYPE_FCP) - rc = reipl_append_ascii_scpdata(dest, len, &ipl_block); - else - dest[0] = 0; - return rc; -} - - -static struct kobj_attribute sys_ipl_vm_parm_attr = - __ATTR(parm, S_IRUGO, ipl_vm_parm_show, NULL); - -static ssize_t sys_ipl_device_show(struct kobject *kobj, - struct kobj_attribute *attr, char *page) -{ - struct ipl_parameter_block *ipl = IPL_PARMBLOCK_START; - - switch (ipl_info.type) { - case IPL_TYPE_CCW: - return sprintf(page, "0.0.%04x\n", ipl_devno); - case IPL_TYPE_FCP: - case IPL_TYPE_FCP_DUMP: - return sprintf(page, "0.0.%04x\n", ipl->ipl_info.fcp.devno); - default: - return 0; - } -} - -static struct kobj_attribute sys_ipl_device_attr = - __ATTR(device, S_IRUGO, sys_ipl_device_show, NULL); - -static ssize_t ipl_parameter_read(struct file *filp, struct kobject *kobj, - struct bin_attribute *attr, char *buf, - loff_t off, size_t count) -{ - return memory_read_from_buffer(buf, count, &off, IPL_PARMBLOCK_START, - IPL_PARMBLOCK_SIZE); -} - -static struct bin_attribute ipl_parameter_attr = { - .attr = { - .name = "binary_parameter", - .mode = S_IRUGO, - }, - .size = PAGE_SIZE, - .read = &ipl_parameter_read, -}; - -static ssize_t ipl_scp_data_read(struct file *filp, struct kobject *kobj, - struct bin_attribute *attr, char *buf, - loff_t off, size_t count) -{ - unsigned int size = IPL_PARMBLOCK_START->ipl_info.fcp.scp_data_len; - void *scp_data = &IPL_PARMBLOCK_START->ipl_info.fcp.scp_data; - - return memory_read_from_buffer(buf, count, &off, scp_data, size); -} - -static struct bin_attribute ipl_scp_data_attr = { - .attr = { - .name = "scp_data", - .mode = S_IRUGO, - }, - .size = PAGE_SIZE, - .read = ipl_scp_data_read, -}; - -/* FCP ipl device attributes */ - -DEFINE_IPL_ATTR_RO(ipl_fcp, wwpn, "0x%016llx\n", (unsigned long long) - IPL_PARMBLOCK_START->ipl_info.fcp.wwpn); -DEFINE_IPL_ATTR_RO(ipl_fcp, lun, "0x%016llx\n", (unsigned long long) - IPL_PARMBLOCK_START->ipl_info.fcp.lun); -DEFINE_IPL_ATTR_RO(ipl_fcp, bootprog, "%lld\n", (unsigned long long) - IPL_PARMBLOCK_START->ipl_info.fcp.bootprog); -DEFINE_IPL_ATTR_RO(ipl_fcp, br_lba, "%lld\n", (unsigned long long) - IPL_PARMBLOCK_START->ipl_info.fcp.br_lba); - -static struct attribute *ipl_fcp_attrs[] = { - &sys_ipl_type_attr.attr, - &sys_ipl_device_attr.attr, - &sys_ipl_fcp_wwpn_attr.attr, - &sys_ipl_fcp_lun_attr.attr, - &sys_ipl_fcp_bootprog_attr.attr, - &sys_ipl_fcp_br_lba_attr.attr, - NULL, -}; - -static struct attribute_group ipl_fcp_attr_group = { - .attrs = ipl_fcp_attrs, -}; - -/* CCW ipl device attributes */ - -static ssize_t ipl_ccw_loadparm_show(struct kobject *kobj, - struct kobj_attribute *attr, char *page) -{ - char loadparm[LOADPARM_LEN + 1] = {}; - - if (!sclp_ipl_info.is_valid) - return sprintf(page, "#unknown#\n"); - memcpy(loadparm, &sclp_ipl_info.loadparm, LOADPARM_LEN); - EBCASC(loadparm, LOADPARM_LEN); - strim(loadparm); - return sprintf(page, "%s\n", loadparm); -} - -static struct kobj_attribute sys_ipl_ccw_loadparm_attr = - __ATTR(loadparm, 0444, ipl_ccw_loadparm_show, NULL); - -static struct attribute *ipl_ccw_attrs_vm[] = { - &sys_ipl_type_attr.attr, - &sys_ipl_device_attr.attr, - &sys_ipl_ccw_loadparm_attr.attr, - &sys_ipl_vm_parm_attr.attr, - NULL, -}; - -static struct attribute *ipl_ccw_attrs_lpar[] = { - &sys_ipl_type_attr.attr, - &sys_ipl_device_attr.attr, - &sys_ipl_ccw_loadparm_attr.attr, - NULL, -}; - -static struct attribute_group ipl_ccw_attr_group_vm = { - .attrs = ipl_ccw_attrs_vm, -}; - -static struct attribute_group ipl_ccw_attr_group_lpar = { - .attrs = ipl_ccw_attrs_lpar -}; - -/* NSS ipl device attributes */ - -DEFINE_IPL_ATTR_RO(ipl_nss, name, "%s\n", kernel_nss_name); - -static struct attribute *ipl_nss_attrs[] = { - &sys_ipl_type_attr.attr, - &sys_ipl_nss_name_attr.attr, - &sys_ipl_ccw_loadparm_attr.attr, - &sys_ipl_vm_parm_attr.attr, - NULL, -}; - -static struct attribute_group ipl_nss_attr_group = { - .attrs = ipl_nss_attrs, -}; - -/* UNKNOWN ipl device attributes */ - -static struct attribute *ipl_unknown_attrs[] = { - &sys_ipl_type_attr.attr, - NULL, -}; - -static struct attribute_group ipl_unknown_attr_group = { - .attrs = ipl_unknown_attrs, -}; - -static struct kset *ipl_kset; - -static int __init ipl_register_fcp_files(void) -{ - int rc; - - rc = sysfs_create_group(&ipl_kset->kobj, &ipl_fcp_attr_group); - if (rc) - goto out; - rc = sysfs_create_bin_file(&ipl_kset->kobj, &ipl_parameter_attr); - if (rc) - goto out_ipl_parm; - rc = sysfs_create_bin_file(&ipl_kset->kobj, &ipl_scp_data_attr); - if (!rc) - goto out; - - sysfs_remove_bin_file(&ipl_kset->kobj, &ipl_parameter_attr); - -out_ipl_parm: - sysfs_remove_group(&ipl_kset->kobj, &ipl_fcp_attr_group); -out: - return rc; -} - -static void __ipl_run(void *unused) -{ - diag308(DIAG308_IPL, NULL); - if (MACHINE_IS_VM) - __cpcmd("IPL", NULL, 0, NULL); - else if (ipl_info.type == IPL_TYPE_CCW) - reipl_ccw_dev(&ipl_info.data.ccw.dev_id); -} - -static void ipl_run(struct shutdown_trigger *trigger) -{ - smp_call_ipl_cpu(__ipl_run, NULL); -} - -static int __init ipl_init(void) -{ - int rc; - - ipl_kset = kset_create_and_add("ipl", NULL, firmware_kobj); - if (!ipl_kset) { - rc = -ENOMEM; - goto out; - } - switch (ipl_info.type) { - case IPL_TYPE_CCW: - if (MACHINE_IS_VM) - rc = sysfs_create_group(&ipl_kset->kobj, - &ipl_ccw_attr_group_vm); - else - rc = sysfs_create_group(&ipl_kset->kobj, - &ipl_ccw_attr_group_lpar); - break; - case IPL_TYPE_FCP: - case IPL_TYPE_FCP_DUMP: - rc = ipl_register_fcp_files(); - break; - case IPL_TYPE_NSS: - rc = sysfs_create_group(&ipl_kset->kobj, &ipl_nss_attr_group); - break; - default: - rc = sysfs_create_group(&ipl_kset->kobj, - &ipl_unknown_attr_group); - break; - } -out: - if (rc) - panic("ipl_init failed: rc = %i\n", rc); - - return 0; -} - -static struct shutdown_action __refdata ipl_action = { - .name = SHUTDOWN_ACTION_IPL_STR, - .fn = ipl_run, - .init = ipl_init, -}; - -/* - * reipl shutdown action: Reboot Linux on shutdown. - */ - -/* VM IPL PARM attributes */ -static ssize_t reipl_generic_vmparm_show(struct ipl_parameter_block *ipb, - char *page) -{ - char vmparm[DIAG308_VMPARM_SIZE + 1] = {}; - - reipl_get_ascii_vmparm(vmparm, sizeof(vmparm), ipb); - return sprintf(page, "%s\n", vmparm); -} - -static ssize_t reipl_generic_vmparm_store(struct ipl_parameter_block *ipb, - size_t vmparm_max, - const char *buf, size_t len) -{ - int i, ip_len; - - /* ignore trailing newline */ - ip_len = len; - if ((len > 0) && (buf[len - 1] == '\n')) - ip_len--; - - if (ip_len > vmparm_max) - return -EINVAL; - - /* parm is used to store kernel options, check for common chars */ - for (i = 0; i < ip_len; i++) - if (!(isalnum(buf[i]) || isascii(buf[i]) || isprint(buf[i]))) - return -EINVAL; - - memset(ipb->ipl_info.ccw.vm_parm, 0, DIAG308_VMPARM_SIZE); - ipb->ipl_info.ccw.vm_parm_len = ip_len; - if (ip_len > 0) { - ipb->ipl_info.ccw.vm_flags |= DIAG308_VM_FLAGS_VP_VALID; - memcpy(ipb->ipl_info.ccw.vm_parm, buf, ip_len); - ASCEBC(ipb->ipl_info.ccw.vm_parm, ip_len); - } else { - ipb->ipl_info.ccw.vm_flags &= ~DIAG308_VM_FLAGS_VP_VALID; - } - - return len; -} - -/* NSS wrapper */ -static ssize_t reipl_nss_vmparm_show(struct kobject *kobj, - struct kobj_attribute *attr, char *page) -{ - return reipl_generic_vmparm_show(reipl_block_nss, page); -} - -static ssize_t reipl_nss_vmparm_store(struct kobject *kobj, - struct kobj_attribute *attr, - const char *buf, size_t len) -{ - return reipl_generic_vmparm_store(reipl_block_nss, 56, buf, len); -} - -/* CCW wrapper */ -static ssize_t reipl_ccw_vmparm_show(struct kobject *kobj, - struct kobj_attribute *attr, char *page) -{ - return reipl_generic_vmparm_show(reipl_block_ccw, page); -} - -static ssize_t reipl_ccw_vmparm_store(struct kobject *kobj, - struct kobj_attribute *attr, - const char *buf, size_t len) -{ - return reipl_generic_vmparm_store(reipl_block_ccw, 64, buf, len); -} - -static struct kobj_attribute sys_reipl_nss_vmparm_attr = - __ATTR(parm, S_IRUGO | S_IWUSR, reipl_nss_vmparm_show, - reipl_nss_vmparm_store); -static struct kobj_attribute sys_reipl_ccw_vmparm_attr = - __ATTR(parm, S_IRUGO | S_IWUSR, reipl_ccw_vmparm_show, - reipl_ccw_vmparm_store); - -/* FCP reipl device attributes */ - -static ssize_t reipl_fcp_scpdata_read(struct file *filp, struct kobject *kobj, - struct bin_attribute *attr, - char *buf, loff_t off, size_t count) -{ - size_t size = reipl_block_fcp->ipl_info.fcp.scp_data_len; - void *scp_data = reipl_block_fcp->ipl_info.fcp.scp_data; - - return memory_read_from_buffer(buf, count, &off, scp_data, size); -} - -static ssize_t reipl_fcp_scpdata_write(struct file *filp, struct kobject *kobj, - struct bin_attribute *attr, - char *buf, loff_t off, size_t count) -{ - size_t padding; - size_t scpdata_len; - - if (off < 0) - return -EINVAL; - - if (off >= DIAG308_SCPDATA_SIZE) - return -ENOSPC; - - if (count > DIAG308_SCPDATA_SIZE - off) - count = DIAG308_SCPDATA_SIZE - off; - - memcpy(reipl_block_fcp->ipl_info.fcp.scp_data, buf + off, count); - scpdata_len = off + count; - - if (scpdata_len % 8) { - padding = 8 - (scpdata_len % 8); - memset(reipl_block_fcp->ipl_info.fcp.scp_data + scpdata_len, - 0, padding); - scpdata_len += padding; - } - - reipl_block_fcp->ipl_info.fcp.scp_data_len = scpdata_len; - reipl_block_fcp->hdr.len = IPL_PARM_BLK_FCP_LEN + scpdata_len; - reipl_block_fcp->hdr.blk0_len = IPL_PARM_BLK0_FCP_LEN + scpdata_len; - - return count; -} - -static struct bin_attribute sys_reipl_fcp_scp_data_attr = { - .attr = { - .name = "scp_data", - .mode = S_IRUGO | S_IWUSR, - }, - .size = PAGE_SIZE, - .read = reipl_fcp_scpdata_read, - .write = reipl_fcp_scpdata_write, -}; - -DEFINE_IPL_ATTR_RW(reipl_fcp, wwpn, "0x%016llx\n", "%016llx\n", - reipl_block_fcp->ipl_info.fcp.wwpn); -DEFINE_IPL_ATTR_RW(reipl_fcp, lun, "0x%016llx\n", "%016llx\n", - reipl_block_fcp->ipl_info.fcp.lun); -DEFINE_IPL_ATTR_RW(reipl_fcp, bootprog, "%lld\n", "%lld\n", - reipl_block_fcp->ipl_info.fcp.bootprog); -DEFINE_IPL_ATTR_RW(reipl_fcp, br_lba, "%lld\n", "%lld\n", - reipl_block_fcp->ipl_info.fcp.br_lba); -DEFINE_IPL_ATTR_RW(reipl_fcp, device, "0.0.%04llx\n", "0.0.%llx\n", - reipl_block_fcp->ipl_info.fcp.devno); - -static struct attribute *reipl_fcp_attrs[] = { - &sys_reipl_fcp_device_attr.attr, - &sys_reipl_fcp_wwpn_attr.attr, - &sys_reipl_fcp_lun_attr.attr, - &sys_reipl_fcp_bootprog_attr.attr, - &sys_reipl_fcp_br_lba_attr.attr, - NULL, -}; - -static struct attribute_group reipl_fcp_attr_group = { - .attrs = reipl_fcp_attrs, -}; - -/* CCW reipl device attributes */ - -DEFINE_IPL_ATTR_RW(reipl_ccw, device, "0.0.%04llx\n", "0.0.%llx\n", - reipl_block_ccw->ipl_info.ccw.devno); - -static void reipl_get_ascii_loadparm(char *loadparm, - struct ipl_parameter_block *ibp) -{ - memcpy(loadparm, ibp->ipl_info.ccw.load_parm, LOADPARM_LEN); - EBCASC(loadparm, LOADPARM_LEN); - loadparm[LOADPARM_LEN] = 0; - strim(loadparm); -} - -static ssize_t reipl_generic_loadparm_show(struct ipl_parameter_block *ipb, - char *page) -{ - char buf[LOADPARM_LEN + 1]; - - reipl_get_ascii_loadparm(buf, ipb); - return sprintf(page, "%s\n", buf); -} - -static ssize_t reipl_generic_loadparm_store(struct ipl_parameter_block *ipb, - const char *buf, size_t len) -{ - int i, lp_len; - - /* ignore trailing newline */ - lp_len = len; - if ((len > 0) && (buf[len - 1] == '\n')) - lp_len--; - /* loadparm can have max 8 characters and must not start with a blank */ - if ((lp_len > LOADPARM_LEN) || ((lp_len > 0) && (buf[0] == ' '))) - return -EINVAL; - /* loadparm can only contain "a-z,A-Z,0-9,SP,." */ - for (i = 0; i < lp_len; i++) { - if (isalpha(buf[i]) || isdigit(buf[i]) || (buf[i] == ' ') || - (buf[i] == '.')) - continue; - return -EINVAL; - } - /* initialize loadparm with blanks */ - memset(ipb->ipl_info.ccw.load_parm, ' ', LOADPARM_LEN); - /* copy and convert to ebcdic */ - memcpy(ipb->ipl_info.ccw.load_parm, buf, lp_len); - ASCEBC(ipb->ipl_info.ccw.load_parm, LOADPARM_LEN); - return len; -} - -/* NSS wrapper */ -static ssize_t reipl_nss_loadparm_show(struct kobject *kobj, - struct kobj_attribute *attr, char *page) -{ - return reipl_generic_loadparm_show(reipl_block_nss, page); -} - -static ssize_t reipl_nss_loadparm_store(struct kobject *kobj, - struct kobj_attribute *attr, - const char *buf, size_t len) -{ - return reipl_generic_loadparm_store(reipl_block_nss, buf, len); -} - -/* CCW wrapper */ -static ssize_t reipl_ccw_loadparm_show(struct kobject *kobj, - struct kobj_attribute *attr, char *page) -{ - return reipl_generic_loadparm_show(reipl_block_ccw, page); -} - -static ssize_t reipl_ccw_loadparm_store(struct kobject *kobj, - struct kobj_attribute *attr, - const char *buf, size_t len) -{ - return reipl_generic_loadparm_store(reipl_block_ccw, buf, len); -} - -static struct kobj_attribute sys_reipl_ccw_loadparm_attr = - __ATTR(loadparm, S_IRUGO | S_IWUSR, reipl_ccw_loadparm_show, - reipl_ccw_loadparm_store); - -static struct attribute *reipl_ccw_attrs_vm[] = { - &sys_reipl_ccw_device_attr.attr, - &sys_reipl_ccw_loadparm_attr.attr, - &sys_reipl_ccw_vmparm_attr.attr, - NULL, -}; - -static struct attribute *reipl_ccw_attrs_lpar[] = { - &sys_reipl_ccw_device_attr.attr, - &sys_reipl_ccw_loadparm_attr.attr, - NULL, -}; - -static struct attribute_group reipl_ccw_attr_group_vm = { - .name = IPL_CCW_STR, - .attrs = reipl_ccw_attrs_vm, -}; - -static struct attribute_group reipl_ccw_attr_group_lpar = { - .name = IPL_CCW_STR, - .attrs = reipl_ccw_attrs_lpar, -}; - - -/* NSS reipl device attributes */ -static void reipl_get_ascii_nss_name(char *dst, - struct ipl_parameter_block *ipb) -{ - memcpy(dst, ipb->ipl_info.ccw.nss_name, NSS_NAME_SIZE); - EBCASC(dst, NSS_NAME_SIZE); - dst[NSS_NAME_SIZE] = 0; -} - -static ssize_t reipl_nss_name_show(struct kobject *kobj, - struct kobj_attribute *attr, char *page) -{ - char nss_name[NSS_NAME_SIZE + 1] = {}; - - reipl_get_ascii_nss_name(nss_name, reipl_block_nss); - return sprintf(page, "%s\n", nss_name); -} - -static ssize_t reipl_nss_name_store(struct kobject *kobj, - struct kobj_attribute *attr, - const char *buf, size_t len) -{ - int nss_len; - - /* ignore trailing newline */ - nss_len = len; - if ((len > 0) && (buf[len - 1] == '\n')) - nss_len--; - - if (nss_len > NSS_NAME_SIZE) - return -EINVAL; - - memset(reipl_block_nss->ipl_info.ccw.nss_name, 0x40, NSS_NAME_SIZE); - if (nss_len > 0) { - reipl_block_nss->ipl_info.ccw.vm_flags |= - DIAG308_VM_FLAGS_NSS_VALID; - memcpy(reipl_block_nss->ipl_info.ccw.nss_name, buf, nss_len); - ASCEBC(reipl_block_nss->ipl_info.ccw.nss_name, nss_len); - EBC_TOUPPER(reipl_block_nss->ipl_info.ccw.nss_name, nss_len); - } else { - reipl_block_nss->ipl_info.ccw.vm_flags &= - ~DIAG308_VM_FLAGS_NSS_VALID; - } - - return len; -} - -static struct kobj_attribute sys_reipl_nss_name_attr = - __ATTR(name, S_IRUGO | S_IWUSR, reipl_nss_name_show, - reipl_nss_name_store); - -static struct kobj_attribute sys_reipl_nss_loadparm_attr = - __ATTR(loadparm, S_IRUGO | S_IWUSR, reipl_nss_loadparm_show, - reipl_nss_loadparm_store); - -static struct attribute *reipl_nss_attrs[] = { - &sys_reipl_nss_name_attr.attr, - &sys_reipl_nss_loadparm_attr.attr, - &sys_reipl_nss_vmparm_attr.attr, - NULL, -}; - -static struct attribute_group reipl_nss_attr_group = { - .name = IPL_NSS_STR, - .attrs = reipl_nss_attrs, -}; - -static void set_reipl_block_actual(struct ipl_parameter_block *reipl_block) -{ - reipl_block_actual = reipl_block; - os_info_entry_add(OS_INFO_REIPL_BLOCK, reipl_block_actual, - reipl_block->hdr.len); -} - -/* reipl type */ - -static int reipl_set_type(enum ipl_type type) -{ - if (!(reipl_capabilities & type)) - return -EINVAL; - - switch(type) { - case IPL_TYPE_CCW: - if (diag308_set_works) - reipl_method = REIPL_METHOD_CCW_DIAG; - else if (MACHINE_IS_VM) - reipl_method = REIPL_METHOD_CCW_VM; - else - reipl_method = REIPL_METHOD_CCW_CIO; - set_reipl_block_actual(reipl_block_ccw); - break; - case IPL_TYPE_FCP: - if (diag308_set_works) - reipl_method = REIPL_METHOD_FCP_RW_DIAG; - else if (MACHINE_IS_VM) - reipl_method = REIPL_METHOD_FCP_RO_VM; - else - reipl_method = REIPL_METHOD_FCP_RO_DIAG; - set_reipl_block_actual(reipl_block_fcp); - break; - case IPL_TYPE_FCP_DUMP: - reipl_method = REIPL_METHOD_FCP_DUMP; - break; - case IPL_TYPE_NSS: - if (diag308_set_works) - reipl_method = REIPL_METHOD_NSS_DIAG; - else - reipl_method = REIPL_METHOD_NSS; - set_reipl_block_actual(reipl_block_nss); - break; - case IPL_TYPE_UNKNOWN: - reipl_method = REIPL_METHOD_DEFAULT; - break; - default: - BUG(); - } - reipl_type = type; - return 0; -} - -static ssize_t reipl_type_show(struct kobject *kobj, - struct kobj_attribute *attr, char *page) -{ - return sprintf(page, "%s\n", ipl_type_str(reipl_type)); -} - -static ssize_t reipl_type_store(struct kobject *kobj, - struct kobj_attribute *attr, - const char *buf, size_t len) -{ - int rc = -EINVAL; - - if (strncmp(buf, IPL_CCW_STR, strlen(IPL_CCW_STR)) == 0) - rc = reipl_set_type(IPL_TYPE_CCW); - else if (strncmp(buf, IPL_FCP_STR, strlen(IPL_FCP_STR)) == 0) - rc = reipl_set_type(IPL_TYPE_FCP); - else if (strncmp(buf, IPL_NSS_STR, strlen(IPL_NSS_STR)) == 0) - rc = reipl_set_type(IPL_TYPE_NSS); - return (rc != 0) ? rc : len; -} - -static struct kobj_attribute reipl_type_attr = - __ATTR(reipl_type, 0644, reipl_type_show, reipl_type_store); - -static struct kset *reipl_kset; -static struct kset *reipl_fcp_kset; - -static void get_ipl_string(char *dst, struct ipl_parameter_block *ipb, - const enum ipl_method m) -{ - char loadparm[LOADPARM_LEN + 1] = {}; - char vmparm[DIAG308_VMPARM_SIZE + 1] = {}; - char nss_name[NSS_NAME_SIZE + 1] = {}; - size_t pos = 0; - - reipl_get_ascii_loadparm(loadparm, ipb); - reipl_get_ascii_nss_name(nss_name, ipb); - reipl_get_ascii_vmparm(vmparm, sizeof(vmparm), ipb); - - switch (m) { - case REIPL_METHOD_CCW_VM: - pos = sprintf(dst, "IPL %X CLEAR", ipb->ipl_info.ccw.devno); - break; - case REIPL_METHOD_NSS: - pos = sprintf(dst, "IPL %s", nss_name); - break; - default: - break; - } - if (strlen(loadparm) > 0) - pos += sprintf(dst + pos, " LOADPARM '%s'", loadparm); - if (strlen(vmparm) > 0) - sprintf(dst + pos, " PARM %s", vmparm); -} - -static void __reipl_run(void *unused) -{ - struct ccw_dev_id devid; - static char buf[128]; - - switch (reipl_method) { - case REIPL_METHOD_CCW_CIO: - devid.devno = reipl_block_ccw->ipl_info.ccw.devno; - devid.ssid = 0; - reipl_ccw_dev(&devid); - break; - case REIPL_METHOD_CCW_VM: - get_ipl_string(buf, reipl_block_ccw, REIPL_METHOD_CCW_VM); - __cpcmd(buf, NULL, 0, NULL); - break; - case REIPL_METHOD_CCW_DIAG: - diag308(DIAG308_SET, reipl_block_ccw); - diag308(DIAG308_IPL, NULL); - break; - case REIPL_METHOD_FCP_RW_DIAG: - diag308(DIAG308_SET, reipl_block_fcp); - diag308(DIAG308_IPL, NULL); - break; - case REIPL_METHOD_FCP_RO_DIAG: - diag308(DIAG308_IPL, NULL); - break; - case REIPL_METHOD_FCP_RO_VM: - __cpcmd("IPL", NULL, 0, NULL); - break; - case REIPL_METHOD_NSS_DIAG: - diag308(DIAG308_SET, reipl_block_nss); - diag308(DIAG308_IPL, NULL); - break; - case REIPL_METHOD_NSS: - get_ipl_string(buf, reipl_block_nss, REIPL_METHOD_NSS); - __cpcmd(buf, NULL, 0, NULL); - break; - case REIPL_METHOD_DEFAULT: - if (MACHINE_IS_VM) - __cpcmd("IPL", NULL, 0, NULL); - diag308(DIAG308_IPL, NULL); - break; - case REIPL_METHOD_FCP_DUMP: - break; - } - disabled_wait((unsigned long) __builtin_return_address(0)); -} - -static void reipl_run(struct shutdown_trigger *trigger) -{ - smp_call_ipl_cpu(__reipl_run, NULL); -} - -static void reipl_block_ccw_init(struct ipl_parameter_block *ipb) -{ - ipb->hdr.len = IPL_PARM_BLK_CCW_LEN; - ipb->hdr.version = IPL_PARM_BLOCK_VERSION; - ipb->hdr.blk0_len = IPL_PARM_BLK0_CCW_LEN; - ipb->hdr.pbt = DIAG308_IPL_TYPE_CCW; -} - -static void reipl_block_ccw_fill_parms(struct ipl_parameter_block *ipb) -{ - /* LOADPARM */ - /* check if read scp info worked and set loadparm */ - if (sclp_ipl_info.is_valid) - memcpy(ipb->ipl_info.ccw.load_parm, - &sclp_ipl_info.loadparm, LOADPARM_LEN); - else - /* read scp info failed: set empty loadparm (EBCDIC blanks) */ - memset(ipb->ipl_info.ccw.load_parm, 0x40, LOADPARM_LEN); - ipb->hdr.flags = DIAG308_FLAGS_LP_VALID; - - /* VM PARM */ - if (MACHINE_IS_VM && diag308_set_works && - (ipl_block.ipl_info.ccw.vm_flags & DIAG308_VM_FLAGS_VP_VALID)) { - - ipb->ipl_info.ccw.vm_flags |= DIAG308_VM_FLAGS_VP_VALID; - ipb->ipl_info.ccw.vm_parm_len = - ipl_block.ipl_info.ccw.vm_parm_len; - memcpy(ipb->ipl_info.ccw.vm_parm, - ipl_block.ipl_info.ccw.vm_parm, DIAG308_VMPARM_SIZE); - } -} - -static int __init reipl_nss_init(void) -{ - int rc; - - if (!MACHINE_IS_VM) - return 0; - - reipl_block_nss = (void *) get_zeroed_page(GFP_KERNEL); - if (!reipl_block_nss) - return -ENOMEM; - - if (!diag308_set_works) - sys_reipl_nss_vmparm_attr.attr.mode = S_IRUGO; - - rc = sysfs_create_group(&reipl_kset->kobj, &reipl_nss_attr_group); - if (rc) - return rc; - - reipl_block_ccw_init(reipl_block_nss); - if (ipl_info.type == IPL_TYPE_NSS) { - memset(reipl_block_nss->ipl_info.ccw.nss_name, - ' ', NSS_NAME_SIZE); - memcpy(reipl_block_nss->ipl_info.ccw.nss_name, - kernel_nss_name, strlen(kernel_nss_name)); - ASCEBC(reipl_block_nss->ipl_info.ccw.nss_name, NSS_NAME_SIZE); - reipl_block_nss->ipl_info.ccw.vm_flags |= - DIAG308_VM_FLAGS_NSS_VALID; - - reipl_block_ccw_fill_parms(reipl_block_nss); - } - - reipl_capabilities |= IPL_TYPE_NSS; - return 0; -} - -static int __init reipl_ccw_init(void) -{ - int rc; - - reipl_block_ccw = (void *) get_zeroed_page(GFP_KERNEL); - if (!reipl_block_ccw) - return -ENOMEM; - - if (MACHINE_IS_VM) { - if (!diag308_set_works) - sys_reipl_ccw_vmparm_attr.attr.mode = S_IRUGO; - rc = sysfs_create_group(&reipl_kset->kobj, - &reipl_ccw_attr_group_vm); - } else { - if(!diag308_set_works) - sys_reipl_ccw_loadparm_attr.attr.mode = S_IRUGO; - rc = sysfs_create_group(&reipl_kset->kobj, - &reipl_ccw_attr_group_lpar); - } - if (rc) - return rc; - - reipl_block_ccw_init(reipl_block_ccw); - if (ipl_info.type == IPL_TYPE_CCW) { - reipl_block_ccw->ipl_info.ccw.devno = ipl_devno; - reipl_block_ccw_fill_parms(reipl_block_ccw); - } - - reipl_capabilities |= IPL_TYPE_CCW; - return 0; -} - -static int __init reipl_fcp_init(void) -{ - int rc; - - if (!diag308_set_works) { - if (ipl_info.type == IPL_TYPE_FCP) { - make_attrs_ro(reipl_fcp_attrs); - sys_reipl_fcp_scp_data_attr.attr.mode = S_IRUGO; - } else - return 0; - } - - reipl_block_fcp = (void *) get_zeroed_page(GFP_KERNEL); - if (!reipl_block_fcp) - return -ENOMEM; - - /* sysfs: create fcp kset for mixing attr group and bin attrs */ - reipl_fcp_kset = kset_create_and_add(IPL_FCP_STR, NULL, - &reipl_kset->kobj); - if (!reipl_fcp_kset) { - free_page((unsigned long) reipl_block_fcp); - return -ENOMEM; - } - - rc = sysfs_create_group(&reipl_fcp_kset->kobj, &reipl_fcp_attr_group); - if (rc) { - kset_unregister(reipl_fcp_kset); - free_page((unsigned long) reipl_block_fcp); - return rc; - } - - rc = sysfs_create_bin_file(&reipl_fcp_kset->kobj, - &sys_reipl_fcp_scp_data_attr); - if (rc) { - sysfs_remove_group(&reipl_fcp_kset->kobj, &reipl_fcp_attr_group); - kset_unregister(reipl_fcp_kset); - free_page((unsigned long) reipl_block_fcp); - return rc; - } - - if (ipl_info.type == IPL_TYPE_FCP) - memcpy(reipl_block_fcp, IPL_PARMBLOCK_START, PAGE_SIZE); - else { - reipl_block_fcp->hdr.len = IPL_PARM_BLK_FCP_LEN; - reipl_block_fcp->hdr.version = IPL_PARM_BLOCK_VERSION; - reipl_block_fcp->hdr.blk0_len = IPL_PARM_BLK0_FCP_LEN; - reipl_block_fcp->hdr.pbt = DIAG308_IPL_TYPE_FCP; - reipl_block_fcp->ipl_info.fcp.opt = DIAG308_IPL_OPT_IPL; - } - reipl_capabilities |= IPL_TYPE_FCP; - return 0; -} - -static int __init reipl_type_init(void) -{ - enum ipl_type reipl_type = ipl_info.type; - struct ipl_parameter_block *reipl_block; - unsigned long size; - - reipl_block = os_info_old_entry(OS_INFO_REIPL_BLOCK, &size); - if (!reipl_block) - goto out; - /* - * If we have an OS info reipl block, this will be used - */ - if (reipl_block->hdr.pbt == DIAG308_IPL_TYPE_FCP) { - memcpy(reipl_block_fcp, reipl_block, size); - reipl_type = IPL_TYPE_FCP; - } else if (reipl_block->hdr.pbt == DIAG308_IPL_TYPE_CCW) { - memcpy(reipl_block_ccw, reipl_block, size); - reipl_type = IPL_TYPE_CCW; - } -out: - return reipl_set_type(reipl_type); -} - -static int __init reipl_init(void) -{ - int rc; - - reipl_kset = kset_create_and_add("reipl", NULL, firmware_kobj); - if (!reipl_kset) - return -ENOMEM; - rc = sysfs_create_file(&reipl_kset->kobj, &reipl_type_attr.attr); - if (rc) { - kset_unregister(reipl_kset); - return rc; - } - rc = reipl_ccw_init(); - if (rc) - return rc; - rc = reipl_fcp_init(); - if (rc) - return rc; - rc = reipl_nss_init(); - if (rc) - return rc; - return reipl_type_init(); -} - -static struct shutdown_action __refdata reipl_action = { - .name = SHUTDOWN_ACTION_REIPL_STR, - .fn = reipl_run, - .init = reipl_init, -}; - -/* - * dump shutdown action: Dump Linux on shutdown. - */ - -/* FCP dump device attributes */ - -DEFINE_IPL_ATTR_RW(dump_fcp, wwpn, "0x%016llx\n", "%016llx\n", - dump_block_fcp->ipl_info.fcp.wwpn); -DEFINE_IPL_ATTR_RW(dump_fcp, lun, "0x%016llx\n", "%016llx\n", - dump_block_fcp->ipl_info.fcp.lun); -DEFINE_IPL_ATTR_RW(dump_fcp, bootprog, "%lld\n", "%lld\n", - dump_block_fcp->ipl_info.fcp.bootprog); -DEFINE_IPL_ATTR_RW(dump_fcp, br_lba, "%lld\n", "%lld\n", - dump_block_fcp->ipl_info.fcp.br_lba); -DEFINE_IPL_ATTR_RW(dump_fcp, device, "0.0.%04llx\n", "0.0.%llx\n", - dump_block_fcp->ipl_info.fcp.devno); - -static struct attribute *dump_fcp_attrs[] = { - &sys_dump_fcp_device_attr.attr, - &sys_dump_fcp_wwpn_attr.attr, - &sys_dump_fcp_lun_attr.attr, - &sys_dump_fcp_bootprog_attr.attr, - &sys_dump_fcp_br_lba_attr.attr, - NULL, -}; - -static struct attribute_group dump_fcp_attr_group = { - .name = IPL_FCP_STR, - .attrs = dump_fcp_attrs, -}; - -/* CCW dump device attributes */ - -DEFINE_IPL_ATTR_RW(dump_ccw, device, "0.0.%04llx\n", "0.0.%llx\n", - dump_block_ccw->ipl_info.ccw.devno); - -static struct attribute *dump_ccw_attrs[] = { - &sys_dump_ccw_device_attr.attr, - NULL, -}; - -static struct attribute_group dump_ccw_attr_group = { - .name = IPL_CCW_STR, - .attrs = dump_ccw_attrs, -}; - -/* dump type */ - -static int dump_set_type(enum dump_type type) -{ - if (!(dump_capabilities & type)) - return -EINVAL; - switch (type) { - case DUMP_TYPE_CCW: - if (diag308_set_works) - dump_method = DUMP_METHOD_CCW_DIAG; - else if (MACHINE_IS_VM) - dump_method = DUMP_METHOD_CCW_VM; - else - dump_method = DUMP_METHOD_CCW_CIO; - break; - case DUMP_TYPE_FCP: - dump_method = DUMP_METHOD_FCP_DIAG; - break; - default: - dump_method = DUMP_METHOD_NONE; - } - dump_type = type; - return 0; -} - -static ssize_t dump_type_show(struct kobject *kobj, - struct kobj_attribute *attr, char *page) -{ - return sprintf(page, "%s\n", dump_type_str(dump_type)); -} - -static ssize_t dump_type_store(struct kobject *kobj, - struct kobj_attribute *attr, - const char *buf, size_t len) -{ - int rc = -EINVAL; - - if (strncmp(buf, DUMP_NONE_STR, strlen(DUMP_NONE_STR)) == 0) - rc = dump_set_type(DUMP_TYPE_NONE); - else if (strncmp(buf, DUMP_CCW_STR, strlen(DUMP_CCW_STR)) == 0) - rc = dump_set_type(DUMP_TYPE_CCW); - else if (strncmp(buf, DUMP_FCP_STR, strlen(DUMP_FCP_STR)) == 0) - rc = dump_set_type(DUMP_TYPE_FCP); - return (rc != 0) ? rc : len; -} - -static struct kobj_attribute dump_type_attr = - __ATTR(dump_type, 0644, dump_type_show, dump_type_store); - -static struct kset *dump_kset; - -static void __dump_run(void *unused) -{ - struct ccw_dev_id devid; - static char buf[100]; - - switch (dump_method) { - case DUMP_METHOD_CCW_CIO: - devid.devno = dump_block_ccw->ipl_info.ccw.devno; - devid.ssid = 0; - reipl_ccw_dev(&devid); - break; - case DUMP_METHOD_CCW_VM: - sprintf(buf, "STORE STATUS"); - __cpcmd(buf, NULL, 0, NULL); - sprintf(buf, "IPL %X", dump_block_ccw->ipl_info.ccw.devno); - __cpcmd(buf, NULL, 0, NULL); - break; - case DUMP_METHOD_CCW_DIAG: - diag308(DIAG308_SET, dump_block_ccw); - diag308(DIAG308_DUMP, NULL); - break; - case DUMP_METHOD_FCP_DIAG: - diag308(DIAG308_SET, dump_block_fcp); - diag308(DIAG308_DUMP, NULL); - break; - default: - break; - } -} - -static void dump_run(struct shutdown_trigger *trigger) -{ - if (dump_method == DUMP_METHOD_NONE) - return; - smp_send_stop(); - smp_call_ipl_cpu(__dump_run, NULL); -} - -static int __init dump_ccw_init(void) -{ - int rc; - - dump_block_ccw = (void *) get_zeroed_page(GFP_KERNEL); - if (!dump_block_ccw) - return -ENOMEM; - rc = sysfs_create_group(&dump_kset->kobj, &dump_ccw_attr_group); - if (rc) { - free_page((unsigned long)dump_block_ccw); - return rc; - } - dump_block_ccw->hdr.len = IPL_PARM_BLK_CCW_LEN; - dump_block_ccw->hdr.version = IPL_PARM_BLOCK_VERSION; - dump_block_ccw->hdr.blk0_len = IPL_PARM_BLK0_CCW_LEN; - dump_block_ccw->hdr.pbt = DIAG308_IPL_TYPE_CCW; - dump_capabilities |= DUMP_TYPE_CCW; - return 0; -} - -static int __init dump_fcp_init(void) -{ - int rc; - - if (!sclp_ipl_info.has_dump) - return 0; /* LDIPL DUMP is not installed */ - if (!diag308_set_works) - return 0; - dump_block_fcp = (void *) get_zeroed_page(GFP_KERNEL); - if (!dump_block_fcp) - return -ENOMEM; - rc = sysfs_create_group(&dump_kset->kobj, &dump_fcp_attr_group); - if (rc) { - free_page((unsigned long)dump_block_fcp); - return rc; - } - dump_block_fcp->hdr.len = IPL_PARM_BLK_FCP_LEN; - dump_block_fcp->hdr.version = IPL_PARM_BLOCK_VERSION; - dump_block_fcp->hdr.blk0_len = IPL_PARM_BLK0_FCP_LEN; - dump_block_fcp->hdr.pbt = DIAG308_IPL_TYPE_FCP; - dump_block_fcp->ipl_info.fcp.opt = DIAG308_IPL_OPT_DUMP; - dump_capabilities |= DUMP_TYPE_FCP; - return 0; -} - -static int __init dump_init(void) -{ - int rc; - - dump_kset = kset_create_and_add("dump", NULL, firmware_kobj); - if (!dump_kset) - return -ENOMEM; - rc = sysfs_create_file(&dump_kset->kobj, &dump_type_attr.attr); - if (rc) { - kset_unregister(dump_kset); - return rc; - } - rc = dump_ccw_init(); - if (rc) - return rc; - rc = dump_fcp_init(); - if (rc) - return rc; - dump_set_type(DUMP_TYPE_NONE); - return 0; -} - -static struct shutdown_action __refdata dump_action = { - .name = SHUTDOWN_ACTION_DUMP_STR, - .fn = dump_run, - .init = dump_init, -}; - -static void dump_reipl_run(struct shutdown_trigger *trigger) -{ - u32 csum; - - csum = csum_partial(reipl_block_actual, reipl_block_actual->hdr.len, 0); - copy_to_absolute_zero(&S390_lowcore.ipib_checksum, &csum, sizeof(csum)); - copy_to_absolute_zero(&S390_lowcore.ipib, &reipl_block_actual, - sizeof(reipl_block_actual)); - dump_run(trigger); -} - -static int __init dump_reipl_init(void) -{ - if (!diag308_set_works) - return -EOPNOTSUPP; - else - return 0; -} - -static struct shutdown_action __refdata dump_reipl_action = { - .name = SHUTDOWN_ACTION_DUMP_REIPL_STR, - .fn = dump_reipl_run, - .init = dump_reipl_init, -}; - -/* - * vmcmd shutdown action: Trigger vm command on shutdown. - */ - -static char vmcmd_on_reboot[128]; -static char vmcmd_on_panic[128]; -static char vmcmd_on_halt[128]; -static char vmcmd_on_poff[128]; -static char vmcmd_on_restart[128]; - -DEFINE_IPL_ATTR_STR_RW(vmcmd, on_reboot, "%s\n", "%s\n", vmcmd_on_reboot); -DEFINE_IPL_ATTR_STR_RW(vmcmd, on_panic, "%s\n", "%s\n", vmcmd_on_panic); -DEFINE_IPL_ATTR_STR_RW(vmcmd, on_halt, "%s\n", "%s\n", vmcmd_on_halt); -DEFINE_IPL_ATTR_STR_RW(vmcmd, on_poff, "%s\n", "%s\n", vmcmd_on_poff); -DEFINE_IPL_ATTR_STR_RW(vmcmd, on_restart, "%s\n", "%s\n", vmcmd_on_restart); - -static struct attribute *vmcmd_attrs[] = { - &sys_vmcmd_on_reboot_attr.attr, - &sys_vmcmd_on_panic_attr.attr, - &sys_vmcmd_on_halt_attr.attr, - &sys_vmcmd_on_poff_attr.attr, - &sys_vmcmd_on_restart_attr.attr, - NULL, -}; - -static struct attribute_group vmcmd_attr_group = { - .attrs = vmcmd_attrs, -}; - -static struct kset *vmcmd_kset; - -static void vmcmd_run(struct shutdown_trigger *trigger) -{ - char *cmd, *next_cmd; - - if (strcmp(trigger->name, ON_REIPL_STR) == 0) - cmd = vmcmd_on_reboot; - else if (strcmp(trigger->name, ON_PANIC_STR) == 0) - cmd = vmcmd_on_panic; - else if (strcmp(trigger->name, ON_HALT_STR) == 0) - cmd = vmcmd_on_halt; - else if (strcmp(trigger->name, ON_POFF_STR) == 0) - cmd = vmcmd_on_poff; - else if (strcmp(trigger->name, ON_RESTART_STR) == 0) - cmd = vmcmd_on_restart; - else - return; - - if (strlen(cmd) == 0) - return; - do { - next_cmd = strchr(cmd, '\n'); - if (next_cmd) { - next_cmd[0] = 0; - next_cmd += 1; - } - __cpcmd(cmd, NULL, 0, NULL); - cmd = next_cmd; - } while (cmd != NULL); -} - -static int vmcmd_init(void) -{ - if (!MACHINE_IS_VM) - return -EOPNOTSUPP; - vmcmd_kset = kset_create_and_add("vmcmd", NULL, firmware_kobj); - if (!vmcmd_kset) - return -ENOMEM; - return sysfs_create_group(&vmcmd_kset->kobj, &vmcmd_attr_group); -} - -static struct shutdown_action vmcmd_action = {SHUTDOWN_ACTION_VMCMD_STR, - vmcmd_run, vmcmd_init}; - -/* - * stop shutdown action: Stop Linux on shutdown. - */ - -static void stop_run(struct shutdown_trigger *trigger) -{ - if (strcmp(trigger->name, ON_PANIC_STR) == 0 || - strcmp(trigger->name, ON_RESTART_STR) == 0) - disabled_wait((unsigned long) __builtin_return_address(0)); - smp_stop_cpu(); -} - -static struct shutdown_action stop_action = {SHUTDOWN_ACTION_STOP_STR, - stop_run, NULL}; - -/* action list */ - -static struct shutdown_action *shutdown_actions_list[] = { - &ipl_action, &reipl_action, &dump_reipl_action, &dump_action, - &vmcmd_action, &stop_action}; -#define SHUTDOWN_ACTIONS_COUNT (sizeof(shutdown_actions_list) / sizeof(void *)) - -/* - * Trigger section - */ - -static struct kset *shutdown_actions_kset; - -static int set_trigger(const char *buf, struct shutdown_trigger *trigger, - size_t len) -{ - int i; - - for (i = 0; i < SHUTDOWN_ACTIONS_COUNT; i++) { - if (sysfs_streq(buf, shutdown_actions_list[i]->name)) { - if (shutdown_actions_list[i]->init_rc) { - return shutdown_actions_list[i]->init_rc; - } else { - trigger->action = shutdown_actions_list[i]; - return len; - } - } - } - return -EINVAL; -} - -/* on reipl */ - -static struct shutdown_trigger on_reboot_trigger = {ON_REIPL_STR, - &reipl_action}; - -static ssize_t on_reboot_show(struct kobject *kobj, - struct kobj_attribute *attr, char *page) -{ - return sprintf(page, "%s\n", on_reboot_trigger.action->name); -} - -static ssize_t on_reboot_store(struct kobject *kobj, - struct kobj_attribute *attr, - const char *buf, size_t len) -{ - return set_trigger(buf, &on_reboot_trigger, len); -} - -static struct kobj_attribute on_reboot_attr = - __ATTR(on_reboot, 0644, on_reboot_show, on_reboot_store); - -static void do_machine_restart(char *__unused) -{ - smp_send_stop(); - on_reboot_trigger.action->fn(&on_reboot_trigger); - reipl_run(NULL); -} -void (*_machine_restart)(char *command) = do_machine_restart; - -/* on panic */ - -static struct shutdown_trigger on_panic_trigger = {ON_PANIC_STR, &stop_action}; - -static ssize_t on_panic_show(struct kobject *kobj, - struct kobj_attribute *attr, char *page) -{ - return sprintf(page, "%s\n", on_panic_trigger.action->name); -} - -static ssize_t on_panic_store(struct kobject *kobj, - struct kobj_attribute *attr, - const char *buf, size_t len) -{ - return set_trigger(buf, &on_panic_trigger, len); -} - -static struct kobj_attribute on_panic_attr = - __ATTR(on_panic, 0644, on_panic_show, on_panic_store); - -static void do_panic(void) -{ - lgr_info_log(); - on_panic_trigger.action->fn(&on_panic_trigger); - stop_run(&on_panic_trigger); -} - -/* on restart */ - -static struct shutdown_trigger on_restart_trigger = {ON_RESTART_STR, - &stop_action}; - -static ssize_t on_restart_show(struct kobject *kobj, - struct kobj_attribute *attr, char *page) -{ - return sprintf(page, "%s\n", on_restart_trigger.action->name); -} - -static ssize_t on_restart_store(struct kobject *kobj, - struct kobj_attribute *attr, - const char *buf, size_t len) -{ - return set_trigger(buf, &on_restart_trigger, len); -} - -static struct kobj_attribute on_restart_attr = - __ATTR(on_restart, 0644, on_restart_show, on_restart_store); - -static void __do_restart(void *ignore) -{ - smp_send_stop(); -#ifdef CONFIG_CRASH_DUMP - crash_kexec(NULL); -#endif - on_restart_trigger.action->fn(&on_restart_trigger); - stop_run(&on_restart_trigger); -} - -void do_restart(void) -{ - tracing_off(); - debug_locks_off(); - lgr_info_log(); - smp_call_online_cpu(__do_restart, NULL); -} - -/* on halt */ - -static struct shutdown_trigger on_halt_trigger = {ON_HALT_STR, &stop_action}; - -static ssize_t on_halt_show(struct kobject *kobj, - struct kobj_attribute *attr, char *page) -{ - return sprintf(page, "%s\n", on_halt_trigger.action->name); -} - -static ssize_t on_halt_store(struct kobject *kobj, - struct kobj_attribute *attr, - const char *buf, size_t len) -{ - return set_trigger(buf, &on_halt_trigger, len); -} - -static struct kobj_attribute on_halt_attr = - __ATTR(on_halt, 0644, on_halt_show, on_halt_store); - - -static void do_machine_halt(void) -{ - smp_send_stop(); - on_halt_trigger.action->fn(&on_halt_trigger); - stop_run(&on_halt_trigger); -} -void (*_machine_halt)(void) = do_machine_halt; - -/* on power off */ - -static struct shutdown_trigger on_poff_trigger = {ON_POFF_STR, &stop_action}; - -static ssize_t on_poff_show(struct kobject *kobj, - struct kobj_attribute *attr, char *page) -{ - return sprintf(page, "%s\n", on_poff_trigger.action->name); -} - -static ssize_t on_poff_store(struct kobject *kobj, - struct kobj_attribute *attr, - const char *buf, size_t len) -{ - return set_trigger(buf, &on_poff_trigger, len); -} - -static struct kobj_attribute on_poff_attr = - __ATTR(on_poff, 0644, on_poff_show, on_poff_store); - - -static void do_machine_power_off(void) -{ - smp_send_stop(); - on_poff_trigger.action->fn(&on_poff_trigger); - stop_run(&on_poff_trigger); -} -void (*_machine_power_off)(void) = do_machine_power_off; - -static void __init shutdown_triggers_init(void) -{ - shutdown_actions_kset = kset_create_and_add("shutdown_actions", NULL, - firmware_kobj); - if (!shutdown_actions_kset) - goto fail; - if (sysfs_create_file(&shutdown_actions_kset->kobj, - &on_reboot_attr.attr)) - goto fail; - if (sysfs_create_file(&shutdown_actions_kset->kobj, - &on_panic_attr.attr)) - goto fail; - if (sysfs_create_file(&shutdown_actions_kset->kobj, - &on_halt_attr.attr)) - goto fail; - if (sysfs_create_file(&shutdown_actions_kset->kobj, - &on_poff_attr.attr)) - goto fail; - if (sysfs_create_file(&shutdown_actions_kset->kobj, - &on_restart_attr.attr)) - goto fail; - return; -fail: - panic("shutdown_triggers_init failed\n"); -} - -static void __init shutdown_actions_init(void) -{ - int i; - - for (i = 0; i < SHUTDOWN_ACTIONS_COUNT; i++) { - if (!shutdown_actions_list[i]->init) - continue; - shutdown_actions_list[i]->init_rc = - shutdown_actions_list[i]->init(); - } -} - -static int __init s390_ipl_init(void) -{ - sclp_get_ipl_info(&sclp_ipl_info); - shutdown_actions_init(); - shutdown_triggers_init(); - return 0; -} - -__initcall(s390_ipl_init); - -static void __init strncpy_skip_quote(char *dst, char *src, int n) -{ - int sx, dx; - - dx = 0; - for (sx = 0; src[sx] != 0; sx++) { - if (src[sx] == '"') - continue; - dst[dx++] = src[sx]; - if (dx >= n) - break; - } -} - -static int __init vmcmd_on_reboot_setup(char *str) -{ - if (!MACHINE_IS_VM) - return 1; - strncpy_skip_quote(vmcmd_on_reboot, str, 127); - vmcmd_on_reboot[127] = 0; - on_reboot_trigger.action = &vmcmd_action; - return 1; -} -__setup("vmreboot=", vmcmd_on_reboot_setup); - -static int __init vmcmd_on_panic_setup(char *str) -{ - if (!MACHINE_IS_VM) - return 1; - strncpy_skip_quote(vmcmd_on_panic, str, 127); - vmcmd_on_panic[127] = 0; - on_panic_trigger.action = &vmcmd_action; - return 1; -} -__setup("vmpanic=", vmcmd_on_panic_setup); - -static int __init vmcmd_on_halt_setup(char *str) -{ - if (!MACHINE_IS_VM) - return 1; - strncpy_skip_quote(vmcmd_on_halt, str, 127); - vmcmd_on_halt[127] = 0; - on_halt_trigger.action = &vmcmd_action; - return 1; -} -__setup("vmhalt=", vmcmd_on_halt_setup); - -static int __init vmcmd_on_poff_setup(char *str) -{ - if (!MACHINE_IS_VM) - return 1; - strncpy_skip_quote(vmcmd_on_poff, str, 127); - vmcmd_on_poff[127] = 0; - on_poff_trigger.action = &vmcmd_action; - return 1; -} -__setup("vmpoff=", vmcmd_on_poff_setup); - -static int on_panic_notify(struct notifier_block *self, - unsigned long event, void *data) -{ - do_panic(); - return NOTIFY_OK; -} - -static struct notifier_block on_panic_nb = { - .notifier_call = on_panic_notify, - .priority = INT_MIN, -}; - -void __init setup_ipl(void) -{ - ipl_info.type = get_ipl_type(); - switch (ipl_info.type) { - case IPL_TYPE_CCW: - ipl_info.data.ccw.dev_id.devno = ipl_devno; - ipl_info.data.ccw.dev_id.ssid = 0; - break; - case IPL_TYPE_FCP: - case IPL_TYPE_FCP_DUMP: - ipl_info.data.fcp.dev_id.devno = - IPL_PARMBLOCK_START->ipl_info.fcp.devno; - ipl_info.data.fcp.dev_id.ssid = 0; - ipl_info.data.fcp.wwpn = IPL_PARMBLOCK_START->ipl_info.fcp.wwpn; - ipl_info.data.fcp.lun = IPL_PARMBLOCK_START->ipl_info.fcp.lun; - break; - case IPL_TYPE_NSS: - strncpy(ipl_info.data.nss.name, kernel_nss_name, - sizeof(ipl_info.data.nss.name)); - break; - case IPL_TYPE_UNKNOWN: - /* We have no info to copy */ - break; - } - atomic_notifier_chain_register(&panic_notifier_list, &on_panic_nb); -} - -void __init ipl_update_parameters(void) -{ - int rc; - - rc = diag308(DIAG308_STORE, &ipl_block); - if ((rc == DIAG308_RC_OK) || (rc == DIAG308_RC_NOCONFIG)) - diag308_set_works = 1; -} - -void __init ipl_save_parameters(void) -{ - struct cio_iplinfo iplinfo; - void *src, *dst; - - if (cio_get_iplinfo(&iplinfo)) - return; - - ipl_devno = iplinfo.devno; - ipl_flags |= IPL_DEVNO_VALID; - if (!iplinfo.is_qdio) - return; - ipl_flags |= IPL_PARMBLOCK_VALID; - src = (void *)(unsigned long)S390_lowcore.ipl_parmblock_ptr; - dst = (void *)IPL_PARMBLOCK_ORIGIN; - memmove(dst, src, PAGE_SIZE); - S390_lowcore.ipl_parmblock_ptr = IPL_PARMBLOCK_ORIGIN; -} - -static LIST_HEAD(rcall); -static DEFINE_MUTEX(rcall_mutex); - -void register_reset_call(struct reset_call *reset) -{ - mutex_lock(&rcall_mutex); - list_add(&reset->list, &rcall); - mutex_unlock(&rcall_mutex); -} -EXPORT_SYMBOL_GPL(register_reset_call); - -void unregister_reset_call(struct reset_call *reset) -{ - mutex_lock(&rcall_mutex); - list_del(&reset->list); - mutex_unlock(&rcall_mutex); -} -EXPORT_SYMBOL_GPL(unregister_reset_call); - -static void do_reset_calls(void) -{ - struct reset_call *reset; - -#ifdef CONFIG_64BIT - if (diag308_set_works) { - diag308_reset(); - return; - } -#endif - list_for_each_entry(reset, &rcall, list) - reset->fn(); -} - -u32 dump_prefix_page; - -void s390_reset_system(void (*func)(void *), void *data) -{ - struct _lowcore *lc; - - lc = (struct _lowcore *)(unsigned long) store_prefix(); - - /* Stack for interrupt/machine check handler */ - lc->panic_stack = S390_lowcore.panic_stack; - - /* Save prefix page address for dump case */ - dump_prefix_page = (u32)(unsigned long) lc; - - /* Disable prefixing */ - set_prefix(0); - - /* Disable lowcore protection */ - __ctl_clear_bit(0,28); - - /* Set new machine check handler */ - S390_lowcore.mcck_new_psw.mask = psw_kernel_bits | PSW_MASK_DAT; - S390_lowcore.mcck_new_psw.addr = - PSW_ADDR_AMODE | (unsigned long) s390_base_mcck_handler; - - /* Set new program check handler */ - S390_lowcore.program_new_psw.mask = psw_kernel_bits | PSW_MASK_DAT; - S390_lowcore.program_new_psw.addr = - PSW_ADDR_AMODE | (unsigned long) s390_base_pgm_handler; - - /* Store status at absolute zero */ - store_status(); - - do_reset_calls(); - if (func) - func(data); -} diff --git a/ANDROID_3.4.5/arch/s390/kernel/irq.c b/ANDROID_3.4.5/arch/s390/kernel/irq.c deleted file mode 100644 index 8a22c272..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/irq.c +++ /dev/null @@ -1,283 +0,0 @@ -/* - * Copyright IBM Corp. 2004,2011 - * Author(s): Martin Schwidefsky <schwidefsky@de.ibm.com>, - * Holger Smolinski <Holger.Smolinski@de.ibm.com>, - * Thomas Spatzier <tspat@de.ibm.com>, - * - * This file contains interrupt related functions. - */ - -#include <linux/kernel_stat.h> -#include <linux/interrupt.h> -#include <linux/seq_file.h> -#include <linux/proc_fs.h> -#include <linux/profile.h> -#include <linux/module.h> -#include <linux/kernel.h> -#include <linux/ftrace.h> -#include <linux/errno.h> -#include <linux/slab.h> -#include <linux/cpu.h> -#include <asm/irq_regs.h> -#include <asm/cputime.h> -#include <asm/lowcore.h> -#include <asm/irq.h> -#include "entry.h" - -struct irq_class { - char *name; - char *desc; -}; - -static const struct irq_class intrclass_names[] = { - {.name = "EXT" }, - {.name = "I/O" }, - {.name = "CLK", .desc = "[EXT] Clock Comparator" }, - {.name = "EXC", .desc = "[EXT] External Call" }, - {.name = "EMS", .desc = "[EXT] Emergency Signal" }, - {.name = "TMR", .desc = "[EXT] CPU Timer" }, - {.name = "TAL", .desc = "[EXT] Timing Alert" }, - {.name = "PFL", .desc = "[EXT] Pseudo Page Fault" }, - {.name = "DSD", .desc = "[EXT] DASD Diag" }, - {.name = "VRT", .desc = "[EXT] Virtio" }, - {.name = "SCP", .desc = "[EXT] Service Call" }, - {.name = "IUC", .desc = "[EXT] IUCV" }, - {.name = "CPM", .desc = "[EXT] CPU Measurement" }, - {.name = "CIO", .desc = "[I/O] Common I/O Layer Interrupt" }, - {.name = "QAI", .desc = "[I/O] QDIO Adapter Interrupt" }, - {.name = "DAS", .desc = "[I/O] DASD" }, - {.name = "C15", .desc = "[I/O] 3215" }, - {.name = "C70", .desc = "[I/O] 3270" }, - {.name = "TAP", .desc = "[I/O] Tape" }, - {.name = "VMR", .desc = "[I/O] Unit Record Devices" }, - {.name = "LCS", .desc = "[I/O] LCS" }, - {.name = "CLW", .desc = "[I/O] CLAW" }, - {.name = "CTC", .desc = "[I/O] CTC" }, - {.name = "APB", .desc = "[I/O] AP Bus" }, - {.name = "CSC", .desc = "[I/O] CHSC Subchannel" }, - {.name = "NMI", .desc = "[NMI] Machine Check" }, -}; - -/* - * show_interrupts is needed by /proc/interrupts. - */ -int show_interrupts(struct seq_file *p, void *v) -{ - int i = *(loff_t *) v, j; - - get_online_cpus(); - if (i == 0) { - seq_puts(p, " "); - for_each_online_cpu(j) - seq_printf(p, "CPU%d ",j); - seq_putc(p, '\n'); - } - - if (i < NR_IRQS) { - seq_printf(p, "%s: ", intrclass_names[i].name); -#ifndef CONFIG_SMP - seq_printf(p, "%10u ", kstat_irqs(i)); -#else - for_each_online_cpu(j) - seq_printf(p, "%10u ", kstat_cpu(j).irqs[i]); -#endif - if (intrclass_names[i].desc) - seq_printf(p, " %s", intrclass_names[i].desc); - seq_putc(p, '\n'); - } - put_online_cpus(); - return 0; -} - -/* - * Switch to the asynchronous interrupt stack for softirq execution. - */ -asmlinkage void do_softirq(void) -{ - unsigned long flags, old, new; - - if (in_interrupt()) - return; - - local_irq_save(flags); - - if (local_softirq_pending()) { - /* Get current stack pointer. */ - asm volatile("la %0,0(15)" : "=a" (old)); - /* Check against async. stack address range. */ - new = S390_lowcore.async_stack; - if (((new - old) >> (PAGE_SHIFT + THREAD_ORDER)) != 0) { - /* Need to switch to the async. stack. */ - new -= STACK_FRAME_OVERHEAD; - ((struct stack_frame *) new)->back_chain = old; - - asm volatile(" la 15,0(%0)\n" - " basr 14,%2\n" - " la 15,0(%1)\n" - : : "a" (new), "a" (old), - "a" (__do_softirq) - : "0", "1", "2", "3", "4", "5", "14", - "cc", "memory" ); - } else { - /* We are already on the async stack. */ - __do_softirq(); - } - } - - local_irq_restore(flags); -} - -#ifdef CONFIG_PROC_FS -void init_irq_proc(void) -{ - struct proc_dir_entry *root_irq_dir; - - root_irq_dir = proc_mkdir("irq", NULL); - create_prof_cpu_mask(root_irq_dir); -} -#endif - -/* - * ext_int_hash[index] is the list head for all external interrupts that hash - * to this index. - */ -static struct list_head ext_int_hash[256]; - -struct ext_int_info { - ext_int_handler_t handler; - u16 code; - struct list_head entry; - struct rcu_head rcu; -}; - -/* ext_int_hash_lock protects the handler lists for external interrupts */ -DEFINE_SPINLOCK(ext_int_hash_lock); - -static void __init init_external_interrupts(void) -{ - int idx; - - for (idx = 0; idx < ARRAY_SIZE(ext_int_hash); idx++) - INIT_LIST_HEAD(&ext_int_hash[idx]); -} - -static inline int ext_hash(u16 code) -{ - return (code + (code >> 9)) & 0xff; -} - -int register_external_interrupt(u16 code, ext_int_handler_t handler) -{ - struct ext_int_info *p; - unsigned long flags; - int index; - - p = kmalloc(sizeof(*p), GFP_ATOMIC); - if (!p) - return -ENOMEM; - p->code = code; - p->handler = handler; - index = ext_hash(code); - - spin_lock_irqsave(&ext_int_hash_lock, flags); - list_add_rcu(&p->entry, &ext_int_hash[index]); - spin_unlock_irqrestore(&ext_int_hash_lock, flags); - return 0; -} -EXPORT_SYMBOL(register_external_interrupt); - -int unregister_external_interrupt(u16 code, ext_int_handler_t handler) -{ - struct ext_int_info *p; - unsigned long flags; - int index = ext_hash(code); - - spin_lock_irqsave(&ext_int_hash_lock, flags); - list_for_each_entry_rcu(p, &ext_int_hash[index], entry) { - if (p->code == code && p->handler == handler) { - list_del_rcu(&p->entry); - kfree_rcu(p, rcu); - } - } - spin_unlock_irqrestore(&ext_int_hash_lock, flags); - return 0; -} -EXPORT_SYMBOL(unregister_external_interrupt); - -void __irq_entry do_extint(struct pt_regs *regs, struct ext_code ext_code, - unsigned int param32, unsigned long param64) -{ - struct pt_regs *old_regs; - struct ext_int_info *p; - int index; - - old_regs = set_irq_regs(regs); - irq_enter(); - if (S390_lowcore.int_clock >= S390_lowcore.clock_comparator) { - /* Serve timer interrupts first. */ - clock_comparator_work(); - } - kstat_cpu(smp_processor_id()).irqs[EXTERNAL_INTERRUPT]++; - if (ext_code.code != 0x1004) - __get_cpu_var(s390_idle).nohz_delay = 1; - - index = ext_hash(ext_code.code); - rcu_read_lock(); - list_for_each_entry_rcu(p, &ext_int_hash[index], entry) - if (likely(p->code == ext_code.code)) - p->handler(ext_code, param32, param64); - rcu_read_unlock(); - irq_exit(); - set_irq_regs(old_regs); -} - -void __init init_IRQ(void) -{ - init_external_interrupts(); -} - -static DEFINE_SPINLOCK(sc_irq_lock); -static int sc_irq_refcount; - -void service_subclass_irq_register(void) -{ - spin_lock(&sc_irq_lock); - if (!sc_irq_refcount) - ctl_set_bit(0, 9); - sc_irq_refcount++; - spin_unlock(&sc_irq_lock); -} -EXPORT_SYMBOL(service_subclass_irq_register); - -void service_subclass_irq_unregister(void) -{ - spin_lock(&sc_irq_lock); - sc_irq_refcount--; - if (!sc_irq_refcount) - ctl_clear_bit(0, 9); - spin_unlock(&sc_irq_lock); -} -EXPORT_SYMBOL(service_subclass_irq_unregister); - -static DEFINE_SPINLOCK(ma_subclass_lock); -static int ma_subclass_refcount; - -void measurement_alert_subclass_register(void) -{ - spin_lock(&ma_subclass_lock); - if (!ma_subclass_refcount) - ctl_set_bit(0, 5); - ma_subclass_refcount++; - spin_unlock(&ma_subclass_lock); -} -EXPORT_SYMBOL(measurement_alert_subclass_register); - -void measurement_alert_subclass_unregister(void) -{ - spin_lock(&ma_subclass_lock); - ma_subclass_refcount--; - if (!ma_subclass_refcount) - ctl_clear_bit(0, 5); - spin_unlock(&ma_subclass_lock); -} -EXPORT_SYMBOL(measurement_alert_subclass_unregister); diff --git a/ANDROID_3.4.5/arch/s390/kernel/jump_label.c b/ANDROID_3.4.5/arch/s390/kernel/jump_label.c deleted file mode 100644 index b987ab2c..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/jump_label.c +++ /dev/null @@ -1,70 +0,0 @@ -/* - * Jump label s390 support - * - * Copyright IBM Corp. 2011 - * Author(s): Jan Glauber <jang@linux.vnet.ibm.com> - */ -#include <linux/module.h> -#include <linux/uaccess.h> -#include <linux/stop_machine.h> -#include <linux/jump_label.h> -#include <asm/ipl.h> - -#ifdef HAVE_JUMP_LABEL - -struct insn { - u16 opcode; - s32 offset; -} __packed; - -struct insn_args { - struct jump_entry *entry; - enum jump_label_type type; -}; - -static void __jump_label_transform(struct jump_entry *entry, - enum jump_label_type type) -{ - struct insn insn; - int rc; - - if (type == JUMP_LABEL_ENABLE) { - /* brcl 15,offset */ - insn.opcode = 0xc0f4; - insn.offset = (entry->target - entry->code) >> 1; - } else { - /* brcl 0,0 */ - insn.opcode = 0xc004; - insn.offset = 0; - } - - rc = probe_kernel_write((void *)entry->code, &insn, JUMP_LABEL_NOP_SIZE); - WARN_ON_ONCE(rc < 0); -} - -static int __sm_arch_jump_label_transform(void *data) -{ - struct insn_args *args = data; - - __jump_label_transform(args->entry, args->type); - return 0; -} - -void arch_jump_label_transform(struct jump_entry *entry, - enum jump_label_type type) -{ - struct insn_args args; - - args.entry = entry; - args.type = type; - - stop_machine(__sm_arch_jump_label_transform, &args, NULL); -} - -void arch_jump_label_transform_static(struct jump_entry *entry, - enum jump_label_type type) -{ - __jump_label_transform(entry, type); -} - -#endif diff --git a/ANDROID_3.4.5/arch/s390/kernel/kprobes.c b/ANDROID_3.4.5/arch/s390/kernel/kprobes.c deleted file mode 100644 index 64b761ae..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/kprobes.c +++ /dev/null @@ -1,671 +0,0 @@ -/* - * Kernel Probes (KProbes) - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program 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 General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. - * - * Copyright (C) IBM Corporation, 2002, 2006 - * - * s390 port, used ppc64 as template. Mike Grundy <grundym@us.ibm.com> - */ - -#include <linux/kprobes.h> -#include <linux/ptrace.h> -#include <linux/preempt.h> -#include <linux/stop_machine.h> -#include <linux/kdebug.h> -#include <linux/uaccess.h> -#include <asm/cacheflush.h> -#include <asm/sections.h> -#include <linux/module.h> -#include <linux/slab.h> -#include <linux/hardirq.h> - -DEFINE_PER_CPU(struct kprobe *, current_kprobe); -DEFINE_PER_CPU(struct kprobe_ctlblk, kprobe_ctlblk); - -struct kretprobe_blackpoint kretprobe_blacklist[] = { }; - -static int __kprobes is_prohibited_opcode(kprobe_opcode_t *insn) -{ - switch (insn[0] >> 8) { - case 0x0c: /* bassm */ - case 0x0b: /* bsm */ - case 0x83: /* diag */ - case 0x44: /* ex */ - case 0xac: /* stnsm */ - case 0xad: /* stosm */ - return -EINVAL; - } - switch (insn[0]) { - case 0x0101: /* pr */ - case 0xb25a: /* bsa */ - case 0xb240: /* bakr */ - case 0xb258: /* bsg */ - case 0xb218: /* pc */ - case 0xb228: /* pt */ - case 0xb98d: /* epsw */ - return -EINVAL; - } - return 0; -} - -static int __kprobes get_fixup_type(kprobe_opcode_t *insn) -{ - /* default fixup method */ - int fixup = FIXUP_PSW_NORMAL; - - switch (insn[0] >> 8) { - case 0x05: /* balr */ - case 0x0d: /* basr */ - fixup = FIXUP_RETURN_REGISTER; - /* if r2 = 0, no branch will be taken */ - if ((insn[0] & 0x0f) == 0) - fixup |= FIXUP_BRANCH_NOT_TAKEN; - break; - case 0x06: /* bctr */ - case 0x07: /* bcr */ - fixup = FIXUP_BRANCH_NOT_TAKEN; - break; - case 0x45: /* bal */ - case 0x4d: /* bas */ - fixup = FIXUP_RETURN_REGISTER; - break; - case 0x47: /* bc */ - case 0x46: /* bct */ - case 0x86: /* bxh */ - case 0x87: /* bxle */ - fixup = FIXUP_BRANCH_NOT_TAKEN; - break; - case 0x82: /* lpsw */ - fixup = FIXUP_NOT_REQUIRED; - break; - case 0xb2: /* lpswe */ - if ((insn[0] & 0xff) == 0xb2) - fixup = FIXUP_NOT_REQUIRED; - break; - case 0xa7: /* bras */ - if ((insn[0] & 0x0f) == 0x05) - fixup |= FIXUP_RETURN_REGISTER; - break; - case 0xc0: - if ((insn[0] & 0x0f) == 0x00 || /* larl */ - (insn[0] & 0x0f) == 0x05) /* brasl */ - fixup |= FIXUP_RETURN_REGISTER; - break; - case 0xeb: - if ((insn[2] & 0xff) == 0x44 || /* bxhg */ - (insn[2] & 0xff) == 0x45) /* bxleg */ - fixup = FIXUP_BRANCH_NOT_TAKEN; - break; - case 0xe3: /* bctg */ - if ((insn[2] & 0xff) == 0x46) - fixup = FIXUP_BRANCH_NOT_TAKEN; - break; - } - return fixup; -} - -int __kprobes arch_prepare_kprobe(struct kprobe *p) -{ - if ((unsigned long) p->addr & 0x01) - return -EINVAL; - - /* Make sure the probe isn't going on a difficult instruction */ - if (is_prohibited_opcode(p->addr)) - return -EINVAL; - - p->opcode = *p->addr; - memcpy(p->ainsn.insn, p->addr, ((p->opcode >> 14) + 3) & -2); - - return 0; -} - -struct ins_replace_args { - kprobe_opcode_t *ptr; - kprobe_opcode_t opcode; -}; - -static int __kprobes swap_instruction(void *aref) -{ - struct kprobe_ctlblk *kcb = get_kprobe_ctlblk(); - unsigned long status = kcb->kprobe_status; - struct ins_replace_args *args = aref; - - kcb->kprobe_status = KPROBE_SWAP_INST; - probe_kernel_write(args->ptr, &args->opcode, sizeof(args->opcode)); - kcb->kprobe_status = status; - return 0; -} - -void __kprobes arch_arm_kprobe(struct kprobe *p) -{ - struct ins_replace_args args; - - args.ptr = p->addr; - args.opcode = BREAKPOINT_INSTRUCTION; - stop_machine(swap_instruction, &args, NULL); -} - -void __kprobes arch_disarm_kprobe(struct kprobe *p) -{ - struct ins_replace_args args; - - args.ptr = p->addr; - args.opcode = p->opcode; - stop_machine(swap_instruction, &args, NULL); -} - -void __kprobes arch_remove_kprobe(struct kprobe *p) -{ -} - -static void __kprobes enable_singlestep(struct kprobe_ctlblk *kcb, - struct pt_regs *regs, - unsigned long ip) -{ - struct per_regs per_kprobe; - - /* Set up the PER control registers %cr9-%cr11 */ - per_kprobe.control = PER_EVENT_IFETCH; - per_kprobe.start = ip; - per_kprobe.end = ip; - - /* Save control regs and psw mask */ - __ctl_store(kcb->kprobe_saved_ctl, 9, 11); - kcb->kprobe_saved_imask = regs->psw.mask & - (PSW_MASK_PER | PSW_MASK_IO | PSW_MASK_EXT); - - /* Set PER control regs, turns on single step for the given address */ - __ctl_load(per_kprobe, 9, 11); - regs->psw.mask |= PSW_MASK_PER; - regs->psw.mask &= ~(PSW_MASK_IO | PSW_MASK_EXT); - regs->psw.addr = ip | PSW_ADDR_AMODE; -} - -static void __kprobes disable_singlestep(struct kprobe_ctlblk *kcb, - struct pt_regs *regs, - unsigned long ip) -{ - /* Restore control regs and psw mask, set new psw address */ - __ctl_load(kcb->kprobe_saved_ctl, 9, 11); - regs->psw.mask &= ~PSW_MASK_PER; - regs->psw.mask |= kcb->kprobe_saved_imask; - regs->psw.addr = ip | PSW_ADDR_AMODE; -} - -/* - * Activate a kprobe by storing its pointer to current_kprobe. The - * previous kprobe is stored in kcb->prev_kprobe. A stack of up to - * two kprobes can be active, see KPROBE_REENTER. - */ -static void __kprobes push_kprobe(struct kprobe_ctlblk *kcb, struct kprobe *p) -{ - kcb->prev_kprobe.kp = __get_cpu_var(current_kprobe); - kcb->prev_kprobe.status = kcb->kprobe_status; - __get_cpu_var(current_kprobe) = p; -} - -/* - * Deactivate a kprobe by backing up to the previous state. If the - * current state is KPROBE_REENTER prev_kprobe.kp will be non-NULL, - * for any other state prev_kprobe.kp will be NULL. - */ -static void __kprobes pop_kprobe(struct kprobe_ctlblk *kcb) -{ - __get_cpu_var(current_kprobe) = kcb->prev_kprobe.kp; - kcb->kprobe_status = kcb->prev_kprobe.status; -} - -void __kprobes arch_prepare_kretprobe(struct kretprobe_instance *ri, - struct pt_regs *regs) -{ - ri->ret_addr = (kprobe_opcode_t *) regs->gprs[14]; - - /* Replace the return addr with trampoline addr */ - regs->gprs[14] = (unsigned long) &kretprobe_trampoline; -} - -static void __kprobes kprobe_reenter_check(struct kprobe_ctlblk *kcb, - struct kprobe *p) -{ - switch (kcb->kprobe_status) { - case KPROBE_HIT_SSDONE: - case KPROBE_HIT_ACTIVE: - kprobes_inc_nmissed_count(p); - break; - case KPROBE_HIT_SS: - case KPROBE_REENTER: - default: - /* - * A kprobe on the code path to single step an instruction - * is a BUG. The code path resides in the .kprobes.text - * section and is executed with interrupts disabled. - */ - printk(KERN_EMERG "Invalid kprobe detected at %p.\n", p->addr); - dump_kprobe(p); - BUG(); - } -} - -static int __kprobes kprobe_handler(struct pt_regs *regs) -{ - struct kprobe_ctlblk *kcb; - struct kprobe *p; - - /* - * We want to disable preemption for the entire duration of kprobe - * processing. That includes the calls to the pre/post handlers - * and single stepping the kprobe instruction. - */ - preempt_disable(); - kcb = get_kprobe_ctlblk(); - p = get_kprobe((void *)((regs->psw.addr & PSW_ADDR_INSN) - 2)); - - if (p) { - if (kprobe_running()) { - /* - * We have hit a kprobe while another is still - * active. This can happen in the pre and post - * handler. Single step the instruction of the - * new probe but do not call any handler function - * of this secondary kprobe. - * push_kprobe and pop_kprobe saves and restores - * the currently active kprobe. - */ - kprobe_reenter_check(kcb, p); - push_kprobe(kcb, p); - kcb->kprobe_status = KPROBE_REENTER; - } else { - /* - * If we have no pre-handler or it returned 0, we - * continue with single stepping. If we have a - * pre-handler and it returned non-zero, it prepped - * for calling the break_handler below on re-entry - * for jprobe processing, so get out doing nothing - * more here. - */ - push_kprobe(kcb, p); - kcb->kprobe_status = KPROBE_HIT_ACTIVE; - if (p->pre_handler && p->pre_handler(p, regs)) - return 1; - kcb->kprobe_status = KPROBE_HIT_SS; - } - enable_singlestep(kcb, regs, (unsigned long) p->ainsn.insn); - return 1; - } else if (kprobe_running()) { - p = __get_cpu_var(current_kprobe); - if (p->break_handler && p->break_handler(p, regs)) { - /* - * Continuation after the jprobe completed and - * caused the jprobe_return trap. The jprobe - * break_handler "returns" to the original - * function that still has the kprobe breakpoint - * installed. We continue with single stepping. - */ - kcb->kprobe_status = KPROBE_HIT_SS; - enable_singlestep(kcb, regs, - (unsigned long) p->ainsn.insn); - return 1; - } /* else: - * No kprobe at this address and the current kprobe - * has no break handler (no jprobe!). The kernel just - * exploded, let the standard trap handler pick up the - * pieces. - */ - } /* else: - * No kprobe at this address and no active kprobe. The trap has - * not been caused by a kprobe breakpoint. The race of breakpoint - * vs. kprobe remove does not exist because on s390 as we use - * stop_machine to arm/disarm the breakpoints. - */ - preempt_enable_no_resched(); - return 0; -} - -/* - * Function return probe trampoline: - * - init_kprobes() establishes a probepoint here - * - When the probed function returns, this probe - * causes the handlers to fire - */ -static void __used kretprobe_trampoline_holder(void) -{ - asm volatile(".global kretprobe_trampoline\n" - "kretprobe_trampoline: bcr 0,0\n"); -} - -/* - * Called when the probe at kretprobe trampoline is hit - */ -static int __kprobes trampoline_probe_handler(struct kprobe *p, - struct pt_regs *regs) -{ - struct kretprobe_instance *ri; - struct hlist_head *head, empty_rp; - struct hlist_node *node, *tmp; - unsigned long flags, orig_ret_address; - unsigned long trampoline_address; - kprobe_opcode_t *correct_ret_addr; - - INIT_HLIST_HEAD(&empty_rp); - kretprobe_hash_lock(current, &head, &flags); - - /* - * It is possible to have multiple instances associated with a given - * task either because an multiple functions in the call path - * have a return probe installed on them, and/or more than one return - * return probe was registered for a target function. - * - * We can handle this because: - * - instances are always inserted at the head of the list - * - when multiple return probes are registered for the same - * function, the first instance's ret_addr will point to the - * real return address, and all the rest will point to - * kretprobe_trampoline - */ - ri = NULL; - orig_ret_address = 0; - correct_ret_addr = NULL; - trampoline_address = (unsigned long) &kretprobe_trampoline; - hlist_for_each_entry_safe(ri, node, tmp, head, hlist) { - if (ri->task != current) - /* another task is sharing our hash bucket */ - continue; - - orig_ret_address = (unsigned long) ri->ret_addr; - - if (orig_ret_address != trampoline_address) - /* - * This is the real return address. Any other - * instances associated with this task are for - * other calls deeper on the call stack - */ - break; - } - - kretprobe_assert(ri, orig_ret_address, trampoline_address); - - correct_ret_addr = ri->ret_addr; - hlist_for_each_entry_safe(ri, node, tmp, head, hlist) { - if (ri->task != current) - /* another task is sharing our hash bucket */ - continue; - - orig_ret_address = (unsigned long) ri->ret_addr; - - if (ri->rp && ri->rp->handler) { - ri->ret_addr = correct_ret_addr; - ri->rp->handler(ri, regs); - } - - recycle_rp_inst(ri, &empty_rp); - - if (orig_ret_address != trampoline_address) - /* - * This is the real return address. Any other - * instances associated with this task are for - * other calls deeper on the call stack - */ - break; - } - - regs->psw.addr = orig_ret_address | PSW_ADDR_AMODE; - - pop_kprobe(get_kprobe_ctlblk()); - kretprobe_hash_unlock(current, &flags); - preempt_enable_no_resched(); - - hlist_for_each_entry_safe(ri, node, tmp, &empty_rp, hlist) { - hlist_del(&ri->hlist); - kfree(ri); - } - /* - * By returning a non-zero value, we are telling - * kprobe_handler() that we don't want the post_handler - * to run (and have re-enabled preemption) - */ - return 1; -} - -/* - * Called after single-stepping. p->addr is the address of the - * instruction whose first byte has been replaced by the "breakpoint" - * instruction. To avoid the SMP problems that can occur when we - * temporarily put back the original opcode to single-step, we - * single-stepped a copy of the instruction. The address of this - * copy is p->ainsn.insn. - */ -static void __kprobes resume_execution(struct kprobe *p, struct pt_regs *regs) -{ - struct kprobe_ctlblk *kcb = get_kprobe_ctlblk(); - unsigned long ip = regs->psw.addr & PSW_ADDR_INSN; - int fixup = get_fixup_type(p->ainsn.insn); - - if (fixup & FIXUP_PSW_NORMAL) - ip += (unsigned long) p->addr - (unsigned long) p->ainsn.insn; - - if (fixup & FIXUP_BRANCH_NOT_TAKEN) { - int ilen = ((p->ainsn.insn[0] >> 14) + 3) & -2; - if (ip - (unsigned long) p->ainsn.insn == ilen) - ip = (unsigned long) p->addr + ilen; - } - - if (fixup & FIXUP_RETURN_REGISTER) { - int reg = (p->ainsn.insn[0] & 0xf0) >> 4; - regs->gprs[reg] += (unsigned long) p->addr - - (unsigned long) p->ainsn.insn; - } - - disable_singlestep(kcb, regs, ip); -} - -static int __kprobes post_kprobe_handler(struct pt_regs *regs) -{ - struct kprobe_ctlblk *kcb = get_kprobe_ctlblk(); - struct kprobe *p = kprobe_running(); - - if (!p) - return 0; - - if (kcb->kprobe_status != KPROBE_REENTER && p->post_handler) { - kcb->kprobe_status = KPROBE_HIT_SSDONE; - p->post_handler(p, regs, 0); - } - - resume_execution(p, regs); - pop_kprobe(kcb); - preempt_enable_no_resched(); - - /* - * if somebody else is singlestepping across a probe point, psw mask - * will have PER set, in which case, continue the remaining processing - * of do_single_step, as if this is not a probe hit. - */ - if (regs->psw.mask & PSW_MASK_PER) - return 0; - - return 1; -} - -static int __kprobes kprobe_trap_handler(struct pt_regs *regs, int trapnr) -{ - struct kprobe_ctlblk *kcb = get_kprobe_ctlblk(); - struct kprobe *p = kprobe_running(); - const struct exception_table_entry *entry; - - switch(kcb->kprobe_status) { - case KPROBE_SWAP_INST: - /* We are here because the instruction replacement failed */ - return 0; - case KPROBE_HIT_SS: - case KPROBE_REENTER: - /* - * We are here because the instruction being single - * stepped caused a page fault. We reset the current - * kprobe and the nip points back to the probe address - * and allow the page fault handler to continue as a - * normal page fault. - */ - disable_singlestep(kcb, regs, (unsigned long) p->addr); - pop_kprobe(kcb); - preempt_enable_no_resched(); - break; - case KPROBE_HIT_ACTIVE: - case KPROBE_HIT_SSDONE: - /* - * We increment the nmissed count for accounting, - * we can also use npre/npostfault count for accouting - * these specific fault cases. - */ - kprobes_inc_nmissed_count(p); - - /* - * We come here because instructions in the pre/post - * handler caused the page_fault, this could happen - * if handler tries to access user space by - * copy_from_user(), get_user() etc. Let the - * user-specified handler try to fix it first. - */ - if (p->fault_handler && p->fault_handler(p, regs, trapnr)) - return 1; - - /* - * In case the user-specified fault handler returned - * zero, try to fix up. - */ - entry = search_exception_tables(regs->psw.addr & PSW_ADDR_INSN); - if (entry) { - regs->psw.addr = entry->fixup | PSW_ADDR_AMODE; - return 1; - } - - /* - * fixup_exception() could not handle it, - * Let do_page_fault() fix it. - */ - break; - default: - break; - } - return 0; -} - -int __kprobes kprobe_fault_handler(struct pt_regs *regs, int trapnr) -{ - int ret; - - if (regs->psw.mask & (PSW_MASK_IO | PSW_MASK_EXT)) - local_irq_disable(); - ret = kprobe_trap_handler(regs, trapnr); - if (regs->psw.mask & (PSW_MASK_IO | PSW_MASK_EXT)) - local_irq_restore(regs->psw.mask & ~PSW_MASK_PER); - return ret; -} - -/* - * Wrapper routine to for handling exceptions. - */ -int __kprobes kprobe_exceptions_notify(struct notifier_block *self, - unsigned long val, void *data) -{ - struct die_args *args = (struct die_args *) data; - struct pt_regs *regs = args->regs; - int ret = NOTIFY_DONE; - - if (regs->psw.mask & (PSW_MASK_IO | PSW_MASK_EXT)) - local_irq_disable(); - - switch (val) { - case DIE_BPT: - if (kprobe_handler(regs)) - ret = NOTIFY_STOP; - break; - case DIE_SSTEP: - if (post_kprobe_handler(regs)) - ret = NOTIFY_STOP; - break; - case DIE_TRAP: - if (!preemptible() && kprobe_running() && - kprobe_trap_handler(regs, args->trapnr)) - ret = NOTIFY_STOP; - break; - default: - break; - } - - if (regs->psw.mask & (PSW_MASK_IO | PSW_MASK_EXT)) - local_irq_restore(regs->psw.mask & ~PSW_MASK_PER); - - return ret; -} - -int __kprobes setjmp_pre_handler(struct kprobe *p, struct pt_regs *regs) -{ - struct jprobe *jp = container_of(p, struct jprobe, kp); - struct kprobe_ctlblk *kcb = get_kprobe_ctlblk(); - unsigned long stack; - - memcpy(&kcb->jprobe_saved_regs, regs, sizeof(struct pt_regs)); - - /* setup return addr to the jprobe handler routine */ - regs->psw.addr = (unsigned long) jp->entry | PSW_ADDR_AMODE; - regs->psw.mask &= ~(PSW_MASK_IO | PSW_MASK_EXT); - - /* r15 is the stack pointer */ - stack = (unsigned long) regs->gprs[15]; - - memcpy(kcb->jprobes_stack, (void *) stack, MIN_STACK_SIZE(stack)); - return 1; -} - -void __kprobes jprobe_return(void) -{ - asm volatile(".word 0x0002"); -} - -static void __used __kprobes jprobe_return_end(void) -{ - asm volatile("bcr 0,0"); -} - -int __kprobes longjmp_break_handler(struct kprobe *p, struct pt_regs *regs) -{ - struct kprobe_ctlblk *kcb = get_kprobe_ctlblk(); - unsigned long stack; - - stack = (unsigned long) kcb->jprobe_saved_regs.gprs[15]; - - /* Put the regs back */ - memcpy(regs, &kcb->jprobe_saved_regs, sizeof(struct pt_regs)); - /* put the stack back */ - memcpy((void *) stack, kcb->jprobes_stack, MIN_STACK_SIZE(stack)); - preempt_enable_no_resched(); - return 1; -} - -static struct kprobe trampoline = { - .addr = (kprobe_opcode_t *) &kretprobe_trampoline, - .pre_handler = trampoline_probe_handler -}; - -int __init arch_init_kprobes(void) -{ - return register_kprobe(&trampoline); -} - -int __kprobes arch_trampoline_kprobe(struct kprobe *p) -{ - return p->addr == (kprobe_opcode_t *) &kretprobe_trampoline; -} diff --git a/ANDROID_3.4.5/arch/s390/kernel/lgr.c b/ANDROID_3.4.5/arch/s390/kernel/lgr.c deleted file mode 100644 index 87f080b1..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/lgr.c +++ /dev/null @@ -1,200 +0,0 @@ -/* - * Linux Guest Relocation (LGR) detection - * - * Copyright IBM Corp. 2012 - * Author(s): Michael Holzheu <holzheu@linux.vnet.ibm.com> - */ - -#include <linux/module.h> -#include <linux/timer.h> -#include <linux/slab.h> -#include <asm/facility.h> -#include <asm/sysinfo.h> -#include <asm/ebcdic.h> -#include <asm/debug.h> -#include <asm/ipl.h> - -#define LGR_TIMER_INTERVAL_SECS (30 * 60) -#define VM_LEVEL_MAX 2 /* Maximum is 8, but we only record two levels */ - -/* - * LGR info: Contains stfle and stsi data - */ -struct lgr_info { - /* Bit field with facility information: 4 DWORDs are stored */ - u64 stfle_fac_list[4]; - /* Level of system (1 = CEC, 2 = LPAR, 3 = z/VM */ - u32 level; - /* Level 1: CEC info (stsi 1.1.1) */ - char manufacturer[16]; - char type[4]; - char sequence[16]; - char plant[4]; - char model[16]; - /* Level 2: LPAR info (stsi 2.2.2) */ - u16 lpar_number; - char name[8]; - /* Level 3: VM info (stsi 3.2.2) */ - u8 vm_count; - struct { - char name[8]; - char cpi[16]; - } vm[VM_LEVEL_MAX]; -} __packed __aligned(8); - -/* - * LGR globals - */ -static void *lgr_page; -static struct lgr_info lgr_info_last; -static struct lgr_info lgr_info_cur; -static struct debug_info *lgr_dbf; - -/* - * Return number of valid stsi levels - */ -static inline int stsi_0(void) -{ - int rc = stsi(NULL, 0, 0, 0); - - return rc == -ENOSYS ? rc : (((unsigned int) rc) >> 28); -} - -/* - * Copy buffer and then convert it to ASCII - */ -static void cpascii(char *dst, char *src, int size) -{ - memcpy(dst, src, size); - EBCASC(dst, size); -} - -/* - * Fill LGR info with 1.1.1 stsi data - */ -static void lgr_stsi_1_1_1(struct lgr_info *lgr_info) -{ - struct sysinfo_1_1_1 *si = lgr_page; - - if (stsi(si, 1, 1, 1) == -ENOSYS) - return; - cpascii(lgr_info->manufacturer, si->manufacturer, - sizeof(si->manufacturer)); - cpascii(lgr_info->type, si->type, sizeof(si->type)); - cpascii(lgr_info->model, si->model, sizeof(si->model)); - cpascii(lgr_info->sequence, si->sequence, sizeof(si->sequence)); - cpascii(lgr_info->plant, si->plant, sizeof(si->plant)); -} - -/* - * Fill LGR info with 2.2.2 stsi data - */ -static void lgr_stsi_2_2_2(struct lgr_info *lgr_info) -{ - struct sysinfo_2_2_2 *si = lgr_page; - - if (stsi(si, 2, 2, 2) == -ENOSYS) - return; - cpascii(lgr_info->name, si->name, sizeof(si->name)); - memcpy(&lgr_info->lpar_number, &si->lpar_number, - sizeof(lgr_info->lpar_number)); -} - -/* - * Fill LGR info with 3.2.2 stsi data - */ -static void lgr_stsi_3_2_2(struct lgr_info *lgr_info) -{ - struct sysinfo_3_2_2 *si = lgr_page; - int i; - - if (stsi(si, 3, 2, 2) == -ENOSYS) - return; - for (i = 0; i < min_t(u8, si->count, VM_LEVEL_MAX); i++) { - cpascii(lgr_info->vm[i].name, si->vm[i].name, - sizeof(si->vm[i].name)); - cpascii(lgr_info->vm[i].cpi, si->vm[i].cpi, - sizeof(si->vm[i].cpi)); - } - lgr_info->vm_count = si->count; -} - -/* - * Fill LGR info with current data - */ -static void lgr_info_get(struct lgr_info *lgr_info) -{ - memset(lgr_info, 0, sizeof(*lgr_info)); - stfle(lgr_info->stfle_fac_list, ARRAY_SIZE(lgr_info->stfle_fac_list)); - lgr_info->level = stsi_0(); - if (lgr_info->level == -ENOSYS) - return; - if (lgr_info->level >= 1) - lgr_stsi_1_1_1(lgr_info); - if (lgr_info->level >= 2) - lgr_stsi_2_2_2(lgr_info); - if (lgr_info->level >= 3) - lgr_stsi_3_2_2(lgr_info); -} - -/* - * Check if LGR info has changed and if yes log new LGR info to s390dbf - */ -void lgr_info_log(void) -{ - static DEFINE_SPINLOCK(lgr_info_lock); - unsigned long flags; - - if (!spin_trylock_irqsave(&lgr_info_lock, flags)) - return; - lgr_info_get(&lgr_info_cur); - if (memcmp(&lgr_info_last, &lgr_info_cur, sizeof(lgr_info_cur)) != 0) { - debug_event(lgr_dbf, 1, &lgr_info_cur, sizeof(lgr_info_cur)); - lgr_info_last = lgr_info_cur; - } - spin_unlock_irqrestore(&lgr_info_lock, flags); -} -EXPORT_SYMBOL_GPL(lgr_info_log); - -static void lgr_timer_set(void); - -/* - * LGR timer callback - */ -static void lgr_timer_fn(unsigned long ignored) -{ - lgr_info_log(); - lgr_timer_set(); -} - -static struct timer_list lgr_timer = - TIMER_DEFERRED_INITIALIZER(lgr_timer_fn, 0, 0); - -/* - * Setup next LGR timer - */ -static void lgr_timer_set(void) -{ - mod_timer(&lgr_timer, jiffies + LGR_TIMER_INTERVAL_SECS * HZ); -} - -/* - * Initialize LGR: Add s390dbf, write initial lgr_info and setup timer - */ -static int __init lgr_init(void) -{ - lgr_page = (void *) __get_free_pages(GFP_KERNEL, 0); - if (!lgr_page) - return -ENOMEM; - lgr_dbf = debug_register("lgr", 1, 1, sizeof(struct lgr_info)); - if (!lgr_dbf) { - free_page((unsigned long) lgr_page); - return -ENOMEM; - } - debug_register_view(lgr_dbf, &debug_hex_ascii_view); - lgr_info_get(&lgr_info_last); - debug_event(lgr_dbf, 1, &lgr_info_last, sizeof(lgr_info_last)); - lgr_timer_set(); - return 0; -} -module_init(lgr_init); diff --git a/ANDROID_3.4.5/arch/s390/kernel/machine_kexec.c b/ANDROID_3.4.5/arch/s390/kernel/machine_kexec.c deleted file mode 100644 index bdad47d5..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/machine_kexec.c +++ /dev/null @@ -1,234 +0,0 @@ -/* - * arch/s390/kernel/machine_kexec.c - * - * Copyright IBM Corp. 2005,2011 - * - * Author(s): Rolf Adelsberger, - * Heiko Carstens <heiko.carstens@de.ibm.com> - * Michael Holzheu <holzheu@linux.vnet.ibm.com> - */ - -#include <linux/device.h> -#include <linux/mm.h> -#include <linux/kexec.h> -#include <linux/delay.h> -#include <linux/reboot.h> -#include <linux/ftrace.h> -#include <linux/debug_locks.h> -#include <asm/cio.h> -#include <asm/setup.h> -#include <asm/pgtable.h> -#include <asm/pgalloc.h> -#include <asm/smp.h> -#include <asm/reset.h> -#include <asm/ipl.h> -#include <asm/diag.h> -#include <asm/asm-offsets.h> - -typedef void (*relocate_kernel_t)(kimage_entry_t *, unsigned long); - -extern const unsigned char relocate_kernel[]; -extern const unsigned long long relocate_kernel_len; - -#ifdef CONFIG_CRASH_DUMP - -void *fill_cpu_elf_notes(void *ptr, struct save_area *sa); - -/* - * Create ELF notes for one CPU - */ -static void add_elf_notes(int cpu) -{ - struct save_area *sa = (void *) 4608 + store_prefix(); - void *ptr; - - memcpy((void *) (4608UL + sa->pref_reg), sa, sizeof(*sa)); - ptr = (u64 *) per_cpu_ptr(crash_notes, cpu); - ptr = fill_cpu_elf_notes(ptr, sa); - memset(ptr, 0, sizeof(struct elf_note)); -} - -/* - * Initialize CPU ELF notes - */ -void setup_regs(void) -{ - unsigned long sa = S390_lowcore.prefixreg_save_area + SAVE_AREA_BASE; - int cpu, this_cpu; - - this_cpu = smp_find_processor_id(stap()); - add_elf_notes(this_cpu); - for_each_online_cpu(cpu) { - if (cpu == this_cpu) - continue; - if (smp_store_status(cpu)) - continue; - add_elf_notes(cpu); - } - /* Copy dump CPU store status info to absolute zero */ - memcpy((void *) SAVE_AREA_BASE, (void *) sa, sizeof(struct save_area)); -} - -#endif - -/* - * Start kdump: We expect here that a store status has been done on our CPU - */ -static void __do_machine_kdump(void *image) -{ -#ifdef CONFIG_CRASH_DUMP - int (*start_kdump)(int) = (void *)((struct kimage *) image)->start; - - __load_psw_mask(PSW_MASK_BASE | PSW_DEFAULT_KEY | PSW_MASK_EA | PSW_MASK_BA); - setup_regs(); - start_kdump(1); -#endif -} - -/* - * Check if kdump checksums are valid: We call purgatory with parameter "0" - */ -static int kdump_csum_valid(struct kimage *image) -{ -#ifdef CONFIG_CRASH_DUMP - int (*start_kdump)(int) = (void *)image->start; - int rc; - - __arch_local_irq_stnsm(0xfb); /* disable DAT */ - rc = start_kdump(0); - __arch_local_irq_stosm(0x04); /* enable DAT */ - return rc ? 0 : -EINVAL; -#else - return -EINVAL; -#endif -} - -/* - * Map or unmap crashkernel memory - */ -static void crash_map_pages(int enable) -{ - unsigned long size = resource_size(&crashk_res); - - BUG_ON(crashk_res.start % KEXEC_CRASH_MEM_ALIGN || - size % KEXEC_CRASH_MEM_ALIGN); - if (enable) - vmem_add_mapping(crashk_res.start, size); - else - vmem_remove_mapping(crashk_res.start, size); -} - -/* - * Map crashkernel memory - */ -void crash_map_reserved_pages(void) -{ - crash_map_pages(1); -} - -/* - * Unmap crashkernel memory - */ -void crash_unmap_reserved_pages(void) -{ - crash_map_pages(0); -} - -/* - * Give back memory to hypervisor before new kdump is loaded - */ -static int machine_kexec_prepare_kdump(void) -{ -#ifdef CONFIG_CRASH_DUMP - if (MACHINE_IS_VM) - diag10_range(PFN_DOWN(crashk_res.start), - PFN_DOWN(crashk_res.end - crashk_res.start + 1)); - return 0; -#else - return -EINVAL; -#endif -} - -int machine_kexec_prepare(struct kimage *image) -{ - void *reboot_code_buffer; - - /* Can't replace kernel image since it is read-only. */ - if (ipl_flags & IPL_NSS_VALID) - return -ENOSYS; - - if (image->type == KEXEC_TYPE_CRASH) - return machine_kexec_prepare_kdump(); - - /* We don't support anything but the default image type for now. */ - if (image->type != KEXEC_TYPE_DEFAULT) - return -EINVAL; - - /* Get the destination where the assembler code should be copied to.*/ - reboot_code_buffer = (void *) page_to_phys(image->control_code_page); - - /* Then copy it */ - memcpy(reboot_code_buffer, relocate_kernel, relocate_kernel_len); - return 0; -} - -void machine_kexec_cleanup(struct kimage *image) -{ -} - -void arch_crash_save_vmcoreinfo(void) -{ - VMCOREINFO_SYMBOL(lowcore_ptr); - VMCOREINFO_SYMBOL(high_memory); - VMCOREINFO_LENGTH(lowcore_ptr, NR_CPUS); -} - -void machine_shutdown(void) -{ -} - -/* - * Do normal kexec - */ -static void __do_machine_kexec(void *data) -{ - relocate_kernel_t data_mover; - struct kimage *image = data; - - data_mover = (relocate_kernel_t) page_to_phys(image->control_code_page); - - /* Call the moving routine */ - (*data_mover)(&image->head, image->start); -} - -/* - * Reset system and call either kdump or normal kexec - */ -static void __machine_kexec(void *data) -{ - struct kimage *image = data; - - pfault_fini(); - tracing_off(); - debug_locks_off(); - if (image->type == KEXEC_TYPE_CRASH) { - lgr_info_log(); - s390_reset_system(__do_machine_kdump, data); - } else { - s390_reset_system(__do_machine_kexec, data); - } - disabled_wait((unsigned long) __builtin_return_address(0)); -} - -/* - * Do either kdump or normal kexec. In case of kdump we first ask - * purgatory, if kdump checksums are valid. - */ -void machine_kexec(struct kimage *image) -{ - if (image->type == KEXEC_TYPE_CRASH && !kdump_csum_valid(image)) - return; - tracer_disable(); - smp_send_stop(); - smp_call_ipl_cpu(__machine_kexec, image); -} diff --git a/ANDROID_3.4.5/arch/s390/kernel/mcount.S b/ANDROID_3.4.5/arch/s390/kernel/mcount.S deleted file mode 100644 index 7e2c38ba..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/mcount.S +++ /dev/null @@ -1,71 +0,0 @@ -/* - * Copyright IBM Corp. 2008,2009 - * - * Author(s): Heiko Carstens <heiko.carstens@de.ibm.com>, - * - */ - -#include <linux/linkage.h> -#include <asm/asm-offsets.h> - - .section .kprobes.text, "ax" - -ENTRY(ftrace_stub) - br %r14 - -ENTRY(_mcount) -#ifdef CONFIG_DYNAMIC_FTRACE - br %r14 - -ENTRY(ftrace_caller) -#endif - stm %r2,%r5,16(%r15) - bras %r1,2f -0: .long ftrace_trace_function -1: .long function_trace_stop -2: l %r2,1b-0b(%r1) - icm %r2,0xf,0(%r2) - jnz 3f - st %r14,56(%r15) - lr %r0,%r15 - ahi %r15,-96 - l %r3,100(%r15) - la %r2,0(%r14) - st %r0,__SF_BACKCHAIN(%r15) - la %r3,0(%r3) - l %r14,0b-0b(%r1) - l %r14,0(%r14) - basr %r14,%r14 -#ifdef CONFIG_FUNCTION_GRAPH_TRACER - l %r2,100(%r15) - l %r3,152(%r15) -ENTRY(ftrace_graph_caller) -# The bras instruction gets runtime patched to call prepare_ftrace_return. -# See ftrace_enable_ftrace_graph_caller. The patched instruction is: -# bras %r14,prepare_ftrace_return - bras %r14,0f -0: st %r2,100(%r15) -#endif - ahi %r15,96 - l %r14,56(%r15) -3: lm %r2,%r5,16(%r15) - br %r14 - -#ifdef CONFIG_FUNCTION_GRAPH_TRACER - -ENTRY(return_to_handler) - stm %r2,%r5,16(%r15) - st %r14,56(%r15) - lr %r0,%r15 - ahi %r15,-96 - st %r0,__SF_BACKCHAIN(%r15) - bras %r1,0f - .long ftrace_return_to_handler -0: l %r2,0b-0b(%r1) - basr %r14,%r2 - lr %r14,%r2 - ahi %r15,96 - lm %r2,%r5,16(%r15) - br %r14 - -#endif diff --git a/ANDROID_3.4.5/arch/s390/kernel/mcount64.S b/ANDROID_3.4.5/arch/s390/kernel/mcount64.S deleted file mode 100644 index f70cadec..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/mcount64.S +++ /dev/null @@ -1,63 +0,0 @@ -/* - * Copyright IBM Corp. 2008,2009 - * - * Author(s): Heiko Carstens <heiko.carstens@de.ibm.com>, - * - */ - -#include <linux/linkage.h> -#include <asm/asm-offsets.h> - - .section .kprobes.text, "ax" - -ENTRY(ftrace_stub) - br %r14 - -ENTRY(_mcount) -#ifdef CONFIG_DYNAMIC_FTRACE - br %r14 - -ENTRY(ftrace_caller) -#endif - larl %r1,function_trace_stop - icm %r1,0xf,0(%r1) - bnzr %r14 - stmg %r2,%r5,32(%r15) - stg %r14,112(%r15) - lgr %r1,%r15 - aghi %r15,-160 - stg %r1,__SF_BACKCHAIN(%r15) - lgr %r2,%r14 - lg %r3,168(%r15) - larl %r14,ftrace_trace_function - lg %r14,0(%r14) - basr %r14,%r14 -#ifdef CONFIG_FUNCTION_GRAPH_TRACER - lg %r2,168(%r15) - lg %r3,272(%r15) -ENTRY(ftrace_graph_caller) -# The bras instruction gets runtime patched to call prepare_ftrace_return. -# See ftrace_enable_ftrace_graph_caller. The patched instruction is: -# bras %r14,prepare_ftrace_return - bras %r14,0f -0: stg %r2,168(%r15) -#endif - aghi %r15,160 - lmg %r2,%r5,32(%r15) - lg %r14,112(%r15) - br %r14 - -#ifdef CONFIG_FUNCTION_GRAPH_TRACER - -ENTRY(return_to_handler) - stmg %r2,%r5,32(%r15) - lgr %r1,%r15 - aghi %r15,-160 - stg %r1,__SF_BACKCHAIN(%r15) - brasl %r14,ftrace_return_to_handler - aghi %r15,160 - lgr %r14,%r2 - lmg %r2,%r5,32(%r15) - br %r14 - -#endif diff --git a/ANDROID_3.4.5/arch/s390/kernel/mem_detect.c b/ANDROID_3.4.5/arch/s390/kernel/mem_detect.c deleted file mode 100644 index 22d502e8..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/mem_detect.c +++ /dev/null @@ -1,145 +0,0 @@ -/* - * Copyright IBM Corp. 2008, 2009 - * - * Author(s): Heiko Carstens <heiko.carstens@de.ibm.com> - */ - -#include <linux/kernel.h> -#include <linux/module.h> -#include <asm/ipl.h> -#include <asm/sclp.h> -#include <asm/setup.h> - -#define ADDR2G (1ULL << 31) - -static void find_memory_chunks(struct mem_chunk chunk[]) -{ - unsigned long long memsize, rnmax, rzm; - unsigned long addr = 0, size; - int i = 0, type; - - rzm = sclp_get_rzm(); - rnmax = sclp_get_rnmax(); - memsize = rzm * rnmax; - if (!rzm) - rzm = 1ULL << 17; - if (sizeof(long) == 4) { - rzm = min(ADDR2G, rzm); - memsize = memsize ? min(ADDR2G, memsize) : ADDR2G; - } - do { - size = 0; - type = tprot(addr); - do { - size += rzm; - if (memsize && addr + size >= memsize) - break; - } while (type == tprot(addr + size)); - if (type == CHUNK_READ_WRITE || type == CHUNK_READ_ONLY) { - chunk[i].addr = addr; - chunk[i].size = size; - chunk[i].type = type; - i++; - } - addr += size; - } while (addr < memsize && i < MEMORY_CHUNKS); -} - -void detect_memory_layout(struct mem_chunk chunk[]) -{ - unsigned long flags, cr0; - - memset(chunk, 0, MEMORY_CHUNKS * sizeof(struct mem_chunk)); - /* Disable IRQs, DAT and low address protection so tprot does the - * right thing and we don't get scheduled away with low address - * protection disabled. - */ - flags = __arch_local_irq_stnsm(0xf8); - __ctl_store(cr0, 0, 0); - __ctl_clear_bit(0, 28); - find_memory_chunks(chunk); - __ctl_load(cr0, 0, 0); - arch_local_irq_restore(flags); -} -EXPORT_SYMBOL(detect_memory_layout); - -/* - * Move memory chunks array from index "from" to index "to" - */ -static void mem_chunk_move(struct mem_chunk chunk[], int to, int from) -{ - int cnt = MEMORY_CHUNKS - to; - - memmove(&chunk[to], &chunk[from], cnt * sizeof(struct mem_chunk)); -} - -/* - * Initialize memory chunk - */ -static void mem_chunk_init(struct mem_chunk *chunk, unsigned long addr, - unsigned long size, int type) -{ - chunk->type = type; - chunk->addr = addr; - chunk->size = size; -} - -/* - * Create memory hole with given address, size, and type - */ -void create_mem_hole(struct mem_chunk chunk[], unsigned long addr, - unsigned long size, int type) -{ - unsigned long lh_start, lh_end, lh_size, ch_start, ch_end, ch_size; - int i, ch_type; - - for (i = 0; i < MEMORY_CHUNKS; i++) { - if (chunk[i].size == 0) - continue; - - /* Define chunk properties */ - ch_start = chunk[i].addr; - ch_size = chunk[i].size; - ch_end = ch_start + ch_size - 1; - ch_type = chunk[i].type; - - /* Is memory chunk hit by memory hole? */ - if (addr + size <= ch_start) - continue; /* No: memory hole in front of chunk */ - if (addr > ch_end) - continue; /* No: memory hole after chunk */ - - /* Yes: Define local hole properties */ - lh_start = max(addr, chunk[i].addr); - lh_end = min(addr + size - 1, ch_end); - lh_size = lh_end - lh_start + 1; - - if (lh_start == ch_start && lh_end == ch_end) { - /* Hole covers complete memory chunk */ - mem_chunk_init(&chunk[i], lh_start, lh_size, type); - } else if (lh_end == ch_end) { - /* Hole starts in memory chunk and convers chunk end */ - mem_chunk_move(chunk, i + 1, i); - mem_chunk_init(&chunk[i], ch_start, ch_size - lh_size, - ch_type); - mem_chunk_init(&chunk[i + 1], lh_start, lh_size, type); - i += 1; - } else if (lh_start == ch_start) { - /* Hole ends in memory chunk */ - mem_chunk_move(chunk, i + 1, i); - mem_chunk_init(&chunk[i], lh_start, lh_size, type); - mem_chunk_init(&chunk[i + 1], lh_end + 1, - ch_size - lh_size, ch_type); - break; - } else { - /* Hole splits memory chunk */ - mem_chunk_move(chunk, i + 2, i); - mem_chunk_init(&chunk[i], ch_start, - lh_start - ch_start, ch_type); - mem_chunk_init(&chunk[i + 1], lh_start, lh_size, type); - mem_chunk_init(&chunk[i + 2], lh_end + 1, - ch_end - lh_end, ch_type); - break; - } - } -} diff --git a/ANDROID_3.4.5/arch/s390/kernel/module.c b/ANDROID_3.4.5/arch/s390/kernel/module.c deleted file mode 100644 index dfcb3436..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/module.c +++ /dev/null @@ -1,395 +0,0 @@ -/* - * arch/s390/kernel/module.c - Kernel module help for s390. - * - * S390 version - * Copyright (C) 2002, 2003 IBM Deutschland Entwicklung GmbH, - * IBM Corporation - * Author(s): Arnd Bergmann (arndb@de.ibm.com) - * Martin Schwidefsky (schwidefsky@de.ibm.com) - * - * based on i386 version - * Copyright (C) 2001 Rusty Russell. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program 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 General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - */ -#include <linux/module.h> -#include <linux/elf.h> -#include <linux/vmalloc.h> -#include <linux/fs.h> -#include <linux/string.h> -#include <linux/kernel.h> -#include <linux/moduleloader.h> -#include <linux/bug.h> - -#if 0 -#define DEBUGP printk -#else -#define DEBUGP(fmt , ...) -#endif - -#ifndef CONFIG_64BIT -#define PLT_ENTRY_SIZE 12 -#else /* CONFIG_64BIT */ -#define PLT_ENTRY_SIZE 20 -#endif /* CONFIG_64BIT */ - -/* Free memory returned from module_alloc */ -void module_free(struct module *mod, void *module_region) -{ - if (mod) { - vfree(mod->arch.syminfo); - mod->arch.syminfo = NULL; - } - vfree(module_region); -} - -static void -check_rela(Elf_Rela *rela, struct module *me) -{ - struct mod_arch_syminfo *info; - - info = me->arch.syminfo + ELF_R_SYM (rela->r_info); - switch (ELF_R_TYPE (rela->r_info)) { - case R_390_GOT12: /* 12 bit GOT offset. */ - case R_390_GOT16: /* 16 bit GOT offset. */ - case R_390_GOT20: /* 20 bit GOT offset. */ - case R_390_GOT32: /* 32 bit GOT offset. */ - case R_390_GOT64: /* 64 bit GOT offset. */ - case R_390_GOTENT: /* 32 bit PC rel. to GOT entry shifted by 1. */ - case R_390_GOTPLT12: /* 12 bit offset to jump slot. */ - case R_390_GOTPLT16: /* 16 bit offset to jump slot. */ - case R_390_GOTPLT20: /* 20 bit offset to jump slot. */ - case R_390_GOTPLT32: /* 32 bit offset to jump slot. */ - case R_390_GOTPLT64: /* 64 bit offset to jump slot. */ - case R_390_GOTPLTENT: /* 32 bit rel. offset to jump slot >> 1. */ - if (info->got_offset == -1UL) { - info->got_offset = me->arch.got_size; - me->arch.got_size += sizeof(void*); - } - break; - case R_390_PLT16DBL: /* 16 bit PC rel. PLT shifted by 1. */ - case R_390_PLT32DBL: /* 32 bit PC rel. PLT shifted by 1. */ - case R_390_PLT32: /* 32 bit PC relative PLT address. */ - case R_390_PLT64: /* 64 bit PC relative PLT address. */ - case R_390_PLTOFF16: /* 16 bit offset from GOT to PLT. */ - case R_390_PLTOFF32: /* 32 bit offset from GOT to PLT. */ - case R_390_PLTOFF64: /* 16 bit offset from GOT to PLT. */ - if (info->plt_offset == -1UL) { - info->plt_offset = me->arch.plt_size; - me->arch.plt_size += PLT_ENTRY_SIZE; - } - break; - case R_390_COPY: - case R_390_GLOB_DAT: - case R_390_JMP_SLOT: - case R_390_RELATIVE: - /* Only needed if we want to support loading of - modules linked with -shared. */ - break; - } -} - -/* - * Account for GOT and PLT relocations. We can't add sections for - * got and plt but we can increase the core module size. - */ -int -module_frob_arch_sections(Elf_Ehdr *hdr, Elf_Shdr *sechdrs, - char *secstrings, struct module *me) -{ - Elf_Shdr *symtab; - Elf_Sym *symbols; - Elf_Rela *rela; - char *strings; - int nrela, i, j; - - /* Find symbol table and string table. */ - symtab = NULL; - for (i = 0; i < hdr->e_shnum; i++) - switch (sechdrs[i].sh_type) { - case SHT_SYMTAB: - symtab = sechdrs + i; - break; - } - if (!symtab) { - printk(KERN_ERR "module %s: no symbol table\n", me->name); - return -ENOEXEC; - } - - /* Allocate one syminfo structure per symbol. */ - me->arch.nsyms = symtab->sh_size / sizeof(Elf_Sym); - me->arch.syminfo = vmalloc(me->arch.nsyms * - sizeof(struct mod_arch_syminfo)); - if (!me->arch.syminfo) - return -ENOMEM; - symbols = (void *) hdr + symtab->sh_offset; - strings = (void *) hdr + sechdrs[symtab->sh_link].sh_offset; - for (i = 0; i < me->arch.nsyms; i++) { - if (symbols[i].st_shndx == SHN_UNDEF && - strcmp(strings + symbols[i].st_name, - "_GLOBAL_OFFSET_TABLE_") == 0) - /* "Define" it as absolute. */ - symbols[i].st_shndx = SHN_ABS; - me->arch.syminfo[i].got_offset = -1UL; - me->arch.syminfo[i].plt_offset = -1UL; - me->arch.syminfo[i].got_initialized = 0; - me->arch.syminfo[i].plt_initialized = 0; - } - - /* Search for got/plt relocations. */ - me->arch.got_size = me->arch.plt_size = 0; - for (i = 0; i < hdr->e_shnum; i++) { - if (sechdrs[i].sh_type != SHT_RELA) - continue; - nrela = sechdrs[i].sh_size / sizeof(Elf_Rela); - rela = (void *) hdr + sechdrs[i].sh_offset; - for (j = 0; j < nrela; j++) - check_rela(rela + j, me); - } - - /* Increase core size by size of got & plt and set start - offsets for got and plt. */ - me->core_size = ALIGN(me->core_size, 4); - me->arch.got_offset = me->core_size; - me->core_size += me->arch.got_size; - me->arch.plt_offset = me->core_size; - me->core_size += me->arch.plt_size; - return 0; -} - -static int -apply_rela(Elf_Rela *rela, Elf_Addr base, Elf_Sym *symtab, - struct module *me) -{ - struct mod_arch_syminfo *info; - Elf_Addr loc, val; - int r_type, r_sym; - - /* This is where to make the change */ - loc = base + rela->r_offset; - /* This is the symbol it is referring to. Note that all - undefined symbols have been resolved. */ - r_sym = ELF_R_SYM(rela->r_info); - r_type = ELF_R_TYPE(rela->r_info); - info = me->arch.syminfo + r_sym; - val = symtab[r_sym].st_value; - - switch (r_type) { - case R_390_8: /* Direct 8 bit. */ - case R_390_12: /* Direct 12 bit. */ - case R_390_16: /* Direct 16 bit. */ - case R_390_20: /* Direct 20 bit. */ - case R_390_32: /* Direct 32 bit. */ - case R_390_64: /* Direct 64 bit. */ - val += rela->r_addend; - if (r_type == R_390_8) - *(unsigned char *) loc = val; - else if (r_type == R_390_12) - *(unsigned short *) loc = (val & 0xfff) | - (*(unsigned short *) loc & 0xf000); - else if (r_type == R_390_16) - *(unsigned short *) loc = val; - else if (r_type == R_390_20) - *(unsigned int *) loc = - (*(unsigned int *) loc & 0xf00000ff) | - (val & 0xfff) << 16 | (val & 0xff000) >> 4; - else if (r_type == R_390_32) - *(unsigned int *) loc = val; - else if (r_type == R_390_64) - *(unsigned long *) loc = val; - break; - case R_390_PC16: /* PC relative 16 bit. */ - case R_390_PC16DBL: /* PC relative 16 bit shifted by 1. */ - case R_390_PC32DBL: /* PC relative 32 bit shifted by 1. */ - case R_390_PC32: /* PC relative 32 bit. */ - case R_390_PC64: /* PC relative 64 bit. */ - val += rela->r_addend - loc; - if (r_type == R_390_PC16) - *(unsigned short *) loc = val; - else if (r_type == R_390_PC16DBL) - *(unsigned short *) loc = val >> 1; - else if (r_type == R_390_PC32DBL) - *(unsigned int *) loc = val >> 1; - else if (r_type == R_390_PC32) - *(unsigned int *) loc = val; - else if (r_type == R_390_PC64) - *(unsigned long *) loc = val; - break; - case R_390_GOT12: /* 12 bit GOT offset. */ - case R_390_GOT16: /* 16 bit GOT offset. */ - case R_390_GOT20: /* 20 bit GOT offset. */ - case R_390_GOT32: /* 32 bit GOT offset. */ - case R_390_GOT64: /* 64 bit GOT offset. */ - case R_390_GOTENT: /* 32 bit PC rel. to GOT entry shifted by 1. */ - case R_390_GOTPLT12: /* 12 bit offset to jump slot. */ - case R_390_GOTPLT20: /* 20 bit offset to jump slot. */ - case R_390_GOTPLT16: /* 16 bit offset to jump slot. */ - case R_390_GOTPLT32: /* 32 bit offset to jump slot. */ - case R_390_GOTPLT64: /* 64 bit offset to jump slot. */ - case R_390_GOTPLTENT: /* 32 bit rel. offset to jump slot >> 1. */ - if (info->got_initialized == 0) { - Elf_Addr *gotent; - - gotent = me->module_core + me->arch.got_offset + - info->got_offset; - *gotent = val; - info->got_initialized = 1; - } - val = info->got_offset + rela->r_addend; - if (r_type == R_390_GOT12 || - r_type == R_390_GOTPLT12) - *(unsigned short *) loc = (val & 0xfff) | - (*(unsigned short *) loc & 0xf000); - else if (r_type == R_390_GOT16 || - r_type == R_390_GOTPLT16) - *(unsigned short *) loc = val; - else if (r_type == R_390_GOT20 || - r_type == R_390_GOTPLT20) - *(unsigned int *) loc = - (*(unsigned int *) loc & 0xf00000ff) | - (val & 0xfff) << 16 | (val & 0xff000) >> 4; - else if (r_type == R_390_GOT32 || - r_type == R_390_GOTPLT32) - *(unsigned int *) loc = val; - else if (r_type == R_390_GOTENT || - r_type == R_390_GOTPLTENT) - *(unsigned int *) loc = - (val + (Elf_Addr) me->module_core - loc) >> 1; - else if (r_type == R_390_GOT64 || - r_type == R_390_GOTPLT64) - *(unsigned long *) loc = val; - break; - case R_390_PLT16DBL: /* 16 bit PC rel. PLT shifted by 1. */ - case R_390_PLT32DBL: /* 32 bit PC rel. PLT shifted by 1. */ - case R_390_PLT32: /* 32 bit PC relative PLT address. */ - case R_390_PLT64: /* 64 bit PC relative PLT address. */ - case R_390_PLTOFF16: /* 16 bit offset from GOT to PLT. */ - case R_390_PLTOFF32: /* 32 bit offset from GOT to PLT. */ - case R_390_PLTOFF64: /* 16 bit offset from GOT to PLT. */ - if (info->plt_initialized == 0) { - unsigned int *ip; - ip = me->module_core + me->arch.plt_offset + - info->plt_offset; -#ifndef CONFIG_64BIT - ip[0] = 0x0d105810; /* basr 1,0; l 1,6(1); br 1 */ - ip[1] = 0x100607f1; - ip[2] = val; -#else /* CONFIG_64BIT */ - ip[0] = 0x0d10e310; /* basr 1,0; lg 1,10(1); br 1 */ - ip[1] = 0x100a0004; - ip[2] = 0x07f10000; - ip[3] = (unsigned int) (val >> 32); - ip[4] = (unsigned int) val; -#endif /* CONFIG_64BIT */ - info->plt_initialized = 1; - } - if (r_type == R_390_PLTOFF16 || - r_type == R_390_PLTOFF32 || - r_type == R_390_PLTOFF64) - val = me->arch.plt_offset - me->arch.got_offset + - info->plt_offset + rela->r_addend; - else { - if (!((r_type == R_390_PLT16DBL && - val - loc + 0xffffUL < 0x1ffffeUL) || - (r_type == R_390_PLT32DBL && - val - loc + 0xffffffffULL < 0x1fffffffeULL))) - val = (Elf_Addr) me->module_core + - me->arch.plt_offset + - info->plt_offset; - val += rela->r_addend - loc; - } - if (r_type == R_390_PLT16DBL) - *(unsigned short *) loc = val >> 1; - else if (r_type == R_390_PLTOFF16) - *(unsigned short *) loc = val; - else if (r_type == R_390_PLT32DBL) - *(unsigned int *) loc = val >> 1; - else if (r_type == R_390_PLT32 || - r_type == R_390_PLTOFF32) - *(unsigned int *) loc = val; - else if (r_type == R_390_PLT64 || - r_type == R_390_PLTOFF64) - *(unsigned long *) loc = val; - break; - case R_390_GOTOFF16: /* 16 bit offset to GOT. */ - case R_390_GOTOFF32: /* 32 bit offset to GOT. */ - case R_390_GOTOFF64: /* 64 bit offset to GOT. */ - val = val + rela->r_addend - - ((Elf_Addr) me->module_core + me->arch.got_offset); - if (r_type == R_390_GOTOFF16) - *(unsigned short *) loc = val; - else if (r_type == R_390_GOTOFF32) - *(unsigned int *) loc = val; - else if (r_type == R_390_GOTOFF64) - *(unsigned long *) loc = val; - break; - case R_390_GOTPC: /* 32 bit PC relative offset to GOT. */ - case R_390_GOTPCDBL: /* 32 bit PC rel. off. to GOT shifted by 1. */ - val = (Elf_Addr) me->module_core + me->arch.got_offset + - rela->r_addend - loc; - if (r_type == R_390_GOTPC) - *(unsigned int *) loc = val; - else if (r_type == R_390_GOTPCDBL) - *(unsigned int *) loc = val >> 1; - break; - case R_390_COPY: - case R_390_GLOB_DAT: /* Create GOT entry. */ - case R_390_JMP_SLOT: /* Create PLT entry. */ - case R_390_RELATIVE: /* Adjust by program base. */ - /* Only needed if we want to support loading of - modules linked with -shared. */ - break; - default: - printk(KERN_ERR "module %s: Unknown relocation: %u\n", - me->name, r_type); - return -ENOEXEC; - } - return 0; -} - -int -apply_relocate_add(Elf_Shdr *sechdrs, const char *strtab, - unsigned int symindex, unsigned int relsec, - struct module *me) -{ - Elf_Addr base; - Elf_Sym *symtab; - Elf_Rela *rela; - unsigned long i, n; - int rc; - - DEBUGP("Applying relocate section %u to %u\n", - relsec, sechdrs[relsec].sh_info); - base = sechdrs[sechdrs[relsec].sh_info].sh_addr; - symtab = (Elf_Sym *) sechdrs[symindex].sh_addr; - rela = (Elf_Rela *) sechdrs[relsec].sh_addr; - n = sechdrs[relsec].sh_size / sizeof(Elf_Rela); - - for (i = 0; i < n; i++, rela++) { - rc = apply_rela(rela, base, symtab, me); - if (rc) - return rc; - } - return 0; -} - -int module_finalize(const Elf_Ehdr *hdr, - const Elf_Shdr *sechdrs, - struct module *me) -{ - vfree(me->arch.syminfo); - me->arch.syminfo = NULL; - return 0; -} diff --git a/ANDROID_3.4.5/arch/s390/kernel/nmi.c b/ANDROID_3.4.5/arch/s390/kernel/nmi.c deleted file mode 100644 index 8c372ca6..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/nmi.c +++ /dev/null @@ -1,375 +0,0 @@ -/* - * Machine check handler - * - * Copyright IBM Corp. 2000,2009 - * Author(s): Ingo Adlung <adlung@de.ibm.com>, - * Martin Schwidefsky <schwidefsky@de.ibm.com>, - * Cornelia Huck <cornelia.huck@de.ibm.com>, - * Heiko Carstens <heiko.carstens@de.ibm.com>, - */ - -#include <linux/kernel_stat.h> -#include <linux/init.h> -#include <linux/errno.h> -#include <linux/hardirq.h> -#include <linux/time.h> -#include <linux/module.h> -#include <asm/lowcore.h> -#include <asm/smp.h> -#include <asm/etr.h> -#include <asm/cputime.h> -#include <asm/nmi.h> -#include <asm/crw.h> - -struct mcck_struct { - int kill_task; - int channel_report; - int warning; - unsigned long long mcck_code; -}; - -static DEFINE_PER_CPU(struct mcck_struct, cpu_mcck); - -static void s390_handle_damage(char *msg) -{ - smp_send_stop(); - disabled_wait((unsigned long) __builtin_return_address(0)); - while (1); -} - -/* - * Main machine check handler function. Will be called with interrupts enabled - * or disabled and machine checks enabled or disabled. - */ -void s390_handle_mcck(void) -{ - unsigned long flags; - struct mcck_struct mcck; - - /* - * Disable machine checks and get the current state of accumulated - * machine checks. Afterwards delete the old state and enable machine - * checks again. - */ - local_irq_save(flags); - local_mcck_disable(); - mcck = __get_cpu_var(cpu_mcck); - memset(&__get_cpu_var(cpu_mcck), 0, sizeof(struct mcck_struct)); - clear_thread_flag(TIF_MCCK_PENDING); - local_mcck_enable(); - local_irq_restore(flags); - - if (mcck.channel_report) - crw_handle_channel_report(); - /* - * A warning may remain for a prolonged period on the bare iron. - * (actually until the machine is powered off, or the problem is gone) - * So we just stop listening for the WARNING MCH and avoid continuously - * being interrupted. One caveat is however, that we must do this per - * processor and cannot use the smp version of ctl_clear_bit(). - * On VM we only get one interrupt per virtally presented machinecheck. - * Though one suffices, we may get one interrupt per (virtual) cpu. - */ - if (mcck.warning) { /* WARNING pending ? */ - static int mchchk_wng_posted = 0; - - /* Use single cpu clear, as we cannot handle smp here. */ - __ctl_clear_bit(14, 24); /* Disable WARNING MCH */ - if (xchg(&mchchk_wng_posted, 1) == 0) - kill_cad_pid(SIGPWR, 1); - } - if (mcck.kill_task) { - local_irq_enable(); - printk(KERN_EMERG "mcck: Terminating task because of machine " - "malfunction (code 0x%016llx).\n", mcck.mcck_code); - printk(KERN_EMERG "mcck: task: %s, pid: %d.\n", - current->comm, current->pid); - do_exit(SIGSEGV); - } -} -EXPORT_SYMBOL_GPL(s390_handle_mcck); - -/* - * returns 0 if all registers could be validated - * returns 1 otherwise - */ -static int notrace s390_revalidate_registers(struct mci *mci) -{ - int kill_task; - u64 zero; - void *fpt_save_area, *fpt_creg_save_area; - - kill_task = 0; - zero = 0; - - if (!mci->gr) { - /* - * General purpose registers couldn't be restored and have - * unknown contents. Process needs to be terminated. - */ - kill_task = 1; - } - if (!mci->fp) { - /* - * Floating point registers can't be restored and - * therefore the process needs to be terminated. - */ - kill_task = 1; - } -#ifndef CONFIG_64BIT - asm volatile( - " ld 0,0(%0)\n" - " ld 2,8(%0)\n" - " ld 4,16(%0)\n" - " ld 6,24(%0)" - : : "a" (&S390_lowcore.floating_pt_save_area)); -#endif - - if (MACHINE_HAS_IEEE) { -#ifdef CONFIG_64BIT - fpt_save_area = &S390_lowcore.floating_pt_save_area; - fpt_creg_save_area = &S390_lowcore.fpt_creg_save_area; -#else - fpt_save_area = (void *) S390_lowcore.extended_save_area_addr; - fpt_creg_save_area = fpt_save_area + 128; -#endif - if (!mci->fc) { - /* - * Floating point control register can't be restored. - * Task will be terminated. - */ - asm volatile("lfpc 0(%0)" : : "a" (&zero), "m" (zero)); - kill_task = 1; - - } else - asm volatile("lfpc 0(%0)" : : "a" (fpt_creg_save_area)); - - asm volatile( - " ld 0,0(%0)\n" - " ld 1,8(%0)\n" - " ld 2,16(%0)\n" - " ld 3,24(%0)\n" - " ld 4,32(%0)\n" - " ld 5,40(%0)\n" - " ld 6,48(%0)\n" - " ld 7,56(%0)\n" - " ld 8,64(%0)\n" - " ld 9,72(%0)\n" - " ld 10,80(%0)\n" - " ld 11,88(%0)\n" - " ld 12,96(%0)\n" - " ld 13,104(%0)\n" - " ld 14,112(%0)\n" - " ld 15,120(%0)\n" - : : "a" (fpt_save_area)); - } - /* Revalidate access registers */ - asm volatile( - " lam 0,15,0(%0)" - : : "a" (&S390_lowcore.access_regs_save_area)); - if (!mci->ar) { - /* - * Access registers have unknown contents. - * Terminating task. - */ - kill_task = 1; - } - /* Revalidate control registers */ - if (!mci->cr) { - /* - * Control registers have unknown contents. - * Can't recover and therefore stopping machine. - */ - s390_handle_damage("invalid control registers."); - } else { -#ifdef CONFIG_64BIT - asm volatile( - " lctlg 0,15,0(%0)" - : : "a" (&S390_lowcore.cregs_save_area)); -#else - asm volatile( - " lctl 0,15,0(%0)" - : : "a" (&S390_lowcore.cregs_save_area)); -#endif - } - /* - * We don't even try to revalidate the TOD register, since we simply - * can't write something sensible into that register. - */ -#ifdef CONFIG_64BIT - /* - * See if we can revalidate the TOD programmable register with its - * old contents (should be zero) otherwise set it to zero. - */ - if (!mci->pr) - asm volatile( - " sr 0,0\n" - " sckpf" - : : : "0", "cc"); - else - asm volatile( - " l 0,0(%0)\n" - " sckpf" - : : "a" (&S390_lowcore.tod_progreg_save_area) - : "0", "cc"); -#endif - /* Revalidate clock comparator register */ - if (S390_lowcore.clock_comparator == -1) - set_clock_comparator(S390_lowcore.mcck_clock); - else - set_clock_comparator(S390_lowcore.clock_comparator); - /* Check if old PSW is valid */ - if (!mci->wp) - /* - * Can't tell if we come from user or kernel mode - * -> stopping machine. - */ - s390_handle_damage("old psw invalid."); - - if (!mci->ms || !mci->pm || !mci->ia) - kill_task = 1; - - return kill_task; -} - -#define MAX_IPD_COUNT 29 -#define MAX_IPD_TIME (5 * 60 * USEC_PER_SEC) /* 5 minutes */ - -#define ED_STP_ISLAND 6 /* External damage STP island check */ -#define ED_STP_SYNC 7 /* External damage STP sync check */ -#define ED_ETR_SYNC 12 /* External damage ETR sync check */ -#define ED_ETR_SWITCH 13 /* External damage ETR switch to local */ - -/* - * machine check handler. - */ -void notrace s390_do_machine_check(struct pt_regs *regs) -{ - static int ipd_count; - static DEFINE_SPINLOCK(ipd_lock); - static unsigned long long last_ipd; - struct mcck_struct *mcck; - unsigned long long tmp; - struct mci *mci; - int umode; - - nmi_enter(); - kstat_cpu(smp_processor_id()).irqs[NMI_NMI]++; - mci = (struct mci *) &S390_lowcore.mcck_interruption_code; - mcck = &__get_cpu_var(cpu_mcck); - umode = user_mode(regs); - - if (mci->sd) { - /* System damage -> stopping machine */ - s390_handle_damage("received system damage machine check."); - } - if (mci->pd) { - if (mci->b) { - /* Processing backup -> verify if we can survive this */ - u64 z_mcic, o_mcic, t_mcic; -#ifdef CONFIG_64BIT - z_mcic = (1ULL<<63 | 1ULL<<59 | 1ULL<<29); - o_mcic = (1ULL<<43 | 1ULL<<42 | 1ULL<<41 | 1ULL<<40 | - 1ULL<<36 | 1ULL<<35 | 1ULL<<34 | 1ULL<<32 | - 1ULL<<30 | 1ULL<<21 | 1ULL<<20 | 1ULL<<17 | - 1ULL<<16); -#else - z_mcic = (1ULL<<63 | 1ULL<<59 | 1ULL<<57 | 1ULL<<50 | - 1ULL<<29); - o_mcic = (1ULL<<43 | 1ULL<<42 | 1ULL<<41 | 1ULL<<40 | - 1ULL<<36 | 1ULL<<35 | 1ULL<<34 | 1ULL<<32 | - 1ULL<<30 | 1ULL<<20 | 1ULL<<17 | 1ULL<<16); -#endif - t_mcic = *(u64 *)mci; - - if (((t_mcic & z_mcic) != 0) || - ((t_mcic & o_mcic) != o_mcic)) { - s390_handle_damage("processing backup machine " - "check with damage."); - } - - /* - * Nullifying exigent condition, therefore we might - * retry this instruction. - */ - spin_lock(&ipd_lock); - tmp = get_clock(); - if (((tmp - last_ipd) >> 12) < MAX_IPD_TIME) - ipd_count++; - else - ipd_count = 1; - last_ipd = tmp; - if (ipd_count == MAX_IPD_COUNT) - s390_handle_damage("too many ipd retries."); - spin_unlock(&ipd_lock); - } else { - /* Processing damage -> stopping machine */ - s390_handle_damage("received instruction processing " - "damage machine check."); - } - } - if (s390_revalidate_registers(mci)) { - if (umode) { - /* - * Couldn't restore all register contents while in - * user mode -> mark task for termination. - */ - mcck->kill_task = 1; - mcck->mcck_code = *(unsigned long long *) mci; - set_thread_flag(TIF_MCCK_PENDING); - } else { - /* - * Couldn't restore all register contents while in - * kernel mode -> stopping machine. - */ - s390_handle_damage("unable to revalidate registers."); - } - } - if (mci->cd) { - /* Timing facility damage */ - s390_handle_damage("TOD clock damaged"); - } - if (mci->ed && mci->ec) { - /* External damage */ - if (S390_lowcore.external_damage_code & (1U << ED_ETR_SYNC)) - etr_sync_check(); - if (S390_lowcore.external_damage_code & (1U << ED_ETR_SWITCH)) - etr_switch_to_local(); - if (S390_lowcore.external_damage_code & (1U << ED_STP_SYNC)) - stp_sync_check(); - if (S390_lowcore.external_damage_code & (1U << ED_STP_ISLAND)) - stp_island_check(); - } - if (mci->se) - /* Storage error uncorrected */ - s390_handle_damage("received storage error uncorrected " - "machine check."); - if (mci->ke) - /* Storage key-error uncorrected */ - s390_handle_damage("received storage key-error uncorrected " - "machine check."); - if (mci->ds && mci->fa) - /* Storage degradation */ - s390_handle_damage("received storage degradation machine " - "check."); - if (mci->cp) { - /* Channel report word pending */ - mcck->channel_report = 1; - set_thread_flag(TIF_MCCK_PENDING); - } - if (mci->w) { - /* Warning pending */ - mcck->warning = 1; - set_thread_flag(TIF_MCCK_PENDING); - } - nmi_exit(); -} - -static int __init machine_check_init(void) -{ - ctl_set_bit(14, 25); /* enable external damage MCH */ - ctl_set_bit(14, 27); /* enable system recovery MCH */ - ctl_set_bit(14, 24); /* enable warning MCH */ - return 0; -} -arch_initcall(machine_check_init); diff --git a/ANDROID_3.4.5/arch/s390/kernel/os_info.c b/ANDROID_3.4.5/arch/s390/kernel/os_info.c deleted file mode 100644 index e8d6c214..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/os_info.c +++ /dev/null @@ -1,168 +0,0 @@ -/* - * OS info memory interface - * - * Copyright IBM Corp. 2012 - * Author(s): Michael Holzheu <holzheu@linux.vnet.ibm.com> - */ - -#define KMSG_COMPONENT "os_info" -#define pr_fmt(fmt) KMSG_COMPONENT ": " fmt - -#include <linux/crash_dump.h> -#include <linux/kernel.h> -#include <asm/checksum.h> -#include <asm/lowcore.h> -#include <asm/os_info.h> - -/* - * OS info structure has to be page aligned - */ -static struct os_info os_info __page_aligned_data; - -/* - * Compute checksum over OS info structure - */ -u32 os_info_csum(struct os_info *os_info) -{ - int size = sizeof(*os_info) - offsetof(struct os_info, version_major); - return csum_partial(&os_info->version_major, size, 0); -} - -/* - * Add crashkernel info to OS info and update checksum - */ -void os_info_crashkernel_add(unsigned long base, unsigned long size) -{ - os_info.crashkernel_addr = (u64)(unsigned long)base; - os_info.crashkernel_size = (u64)(unsigned long)size; - os_info.csum = os_info_csum(&os_info); -} - -/* - * Add OS info entry and update checksum - */ -void os_info_entry_add(int nr, void *ptr, u64 size) -{ - os_info.entry[nr].addr = (u64)(unsigned long)ptr; - os_info.entry[nr].size = size; - os_info.entry[nr].csum = csum_partial(ptr, size, 0); - os_info.csum = os_info_csum(&os_info); -} - -/* - * Initialize OS info struture and set lowcore pointer - */ -void __init os_info_init(void) -{ - void *ptr = &os_info; - - os_info.version_major = OS_INFO_VERSION_MAJOR; - os_info.version_minor = OS_INFO_VERSION_MINOR; - os_info.magic = OS_INFO_MAGIC; - os_info.csum = os_info_csum(&os_info); - copy_to_absolute_zero(&S390_lowcore.os_info, &ptr, sizeof(ptr)); -} - -#ifdef CONFIG_CRASH_DUMP - -static struct os_info *os_info_old; - -/* - * Allocate and copy OS info entry from oldmem - */ -static void os_info_old_alloc(int nr, int align) -{ - unsigned long addr, size = 0; - char *buf, *buf_align, *msg; - u32 csum; - - addr = os_info_old->entry[nr].addr; - if (!addr) { - msg = "not available"; - goto fail; - } - size = os_info_old->entry[nr].size; - buf = kmalloc(size + align - 1, GFP_KERNEL); - if (!buf) { - msg = "alloc failed"; - goto fail; - } - buf_align = PTR_ALIGN(buf, align); - if (copy_from_oldmem(buf_align, (void *) addr, size)) { - msg = "copy failed"; - goto fail_free; - } - csum = csum_partial(buf_align, size, 0); - if (csum != os_info_old->entry[nr].csum) { - msg = "checksum failed"; - goto fail_free; - } - os_info_old->entry[nr].addr = (u64)(unsigned long)buf_align; - msg = "copied"; - goto out; -fail_free: - kfree(buf); -fail: - os_info_old->entry[nr].addr = 0; -out: - pr_info("entry %i: %s (addr=0x%lx size=%lu)\n", - nr, msg, addr, size); -} - -/* - * Initialize os info and os info entries from oldmem - */ -static void os_info_old_init(void) -{ - static int os_info_init; - unsigned long addr; - - if (os_info_init) - return; - if (!OLDMEM_BASE) - goto fail; - if (copy_from_oldmem(&addr, &S390_lowcore.os_info, sizeof(addr))) - goto fail; - if (addr == 0 || addr % PAGE_SIZE) - goto fail; - os_info_old = kzalloc(sizeof(*os_info_old), GFP_KERNEL); - if (!os_info_old) - goto fail; - if (copy_from_oldmem(os_info_old, (void *) addr, sizeof(*os_info_old))) - goto fail_free; - if (os_info_old->magic != OS_INFO_MAGIC) - goto fail_free; - if (os_info_old->csum != os_info_csum(os_info_old)) - goto fail_free; - if (os_info_old->version_major > OS_INFO_VERSION_MAJOR) - goto fail_free; - os_info_old_alloc(OS_INFO_VMCOREINFO, 1); - os_info_old_alloc(OS_INFO_REIPL_BLOCK, 1); - os_info_old_alloc(OS_INFO_INIT_FN, PAGE_SIZE); - pr_info("crashkernel: addr=0x%lx size=%lu\n", - (unsigned long) os_info_old->crashkernel_addr, - (unsigned long) os_info_old->crashkernel_size); - os_info_init = 1; - return; -fail_free: - kfree(os_info_old); -fail: - os_info_init = 1; - os_info_old = NULL; -} - -/* - * Return pointer to os infor entry and its size - */ -void *os_info_old_entry(int nr, unsigned long *size) -{ - os_info_old_init(); - - if (!os_info_old) - return NULL; - if (!os_info_old->entry[nr].addr) - return NULL; - *size = (unsigned long) os_info_old->entry[nr].size; - return (void *)(unsigned long)os_info_old->entry[nr].addr; -} -#endif diff --git a/ANDROID_3.4.5/arch/s390/kernel/perf_cpum_cf.c b/ANDROID_3.4.5/arch/s390/kernel/perf_cpum_cf.c deleted file mode 100644 index cb019f42..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/perf_cpum_cf.c +++ /dev/null @@ -1,690 +0,0 @@ -/* - * Performance event support for s390x - CPU-measurement Counter Facility - * - * Copyright IBM Corp. 2012 - * Author(s): Hendrik Brueckner <brueckner@linux.vnet.ibm.com> - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License (version 2 only) - * as published by the Free Software Foundation. - */ -#define KMSG_COMPONENT "cpum_cf" -#define pr_fmt(fmt) KMSG_COMPONENT ": " fmt - -#include <linux/kernel.h> -#include <linux/kernel_stat.h> -#include <linux/perf_event.h> -#include <linux/percpu.h> -#include <linux/notifier.h> -#include <linux/init.h> -#include <linux/export.h> -#include <asm/ctl_reg.h> -#include <asm/irq.h> -#include <asm/cpu_mf.h> - -/* CPU-measurement counter facility supports these CPU counter sets: - * For CPU counter sets: - * Basic counter set: 0-31 - * Problem-state counter set: 32-63 - * Crypto-activity counter set: 64-127 - * Extented counter set: 128-159 - */ -enum cpumf_ctr_set { - /* CPU counter sets */ - CPUMF_CTR_SET_BASIC = 0, - CPUMF_CTR_SET_USER = 1, - CPUMF_CTR_SET_CRYPTO = 2, - CPUMF_CTR_SET_EXT = 3, - - /* Maximum number of counter sets */ - CPUMF_CTR_SET_MAX, -}; - -#define CPUMF_LCCTL_ENABLE_SHIFT 16 -#define CPUMF_LCCTL_ACTCTL_SHIFT 0 -static const u64 cpumf_state_ctl[CPUMF_CTR_SET_MAX] = { - [CPUMF_CTR_SET_BASIC] = 0x02, - [CPUMF_CTR_SET_USER] = 0x04, - [CPUMF_CTR_SET_CRYPTO] = 0x08, - [CPUMF_CTR_SET_EXT] = 0x01, -}; - -static void ctr_set_enable(u64 *state, int ctr_set) -{ - *state |= cpumf_state_ctl[ctr_set] << CPUMF_LCCTL_ENABLE_SHIFT; -} -static void ctr_set_disable(u64 *state, int ctr_set) -{ - *state &= ~(cpumf_state_ctl[ctr_set] << CPUMF_LCCTL_ENABLE_SHIFT); -} -static void ctr_set_start(u64 *state, int ctr_set) -{ - *state |= cpumf_state_ctl[ctr_set] << CPUMF_LCCTL_ACTCTL_SHIFT; -} -static void ctr_set_stop(u64 *state, int ctr_set) -{ - *state &= ~(cpumf_state_ctl[ctr_set] << CPUMF_LCCTL_ACTCTL_SHIFT); -} - -/* Local CPUMF event structure */ -struct cpu_hw_events { - struct cpumf_ctr_info info; - atomic_t ctr_set[CPUMF_CTR_SET_MAX]; - u64 state, tx_state; - unsigned int flags; -}; -static DEFINE_PER_CPU(struct cpu_hw_events, cpu_hw_events) = { - .ctr_set = { - [CPUMF_CTR_SET_BASIC] = ATOMIC_INIT(0), - [CPUMF_CTR_SET_USER] = ATOMIC_INIT(0), - [CPUMF_CTR_SET_CRYPTO] = ATOMIC_INIT(0), - [CPUMF_CTR_SET_EXT] = ATOMIC_INIT(0), - }, - .state = 0, - .flags = 0, -}; - -static int get_counter_set(u64 event) -{ - int set = -1; - - if (event < 32) - set = CPUMF_CTR_SET_BASIC; - else if (event < 64) - set = CPUMF_CTR_SET_USER; - else if (event < 128) - set = CPUMF_CTR_SET_CRYPTO; - else if (event < 160) - set = CPUMF_CTR_SET_EXT; - - return set; -} - -static int validate_event(const struct hw_perf_event *hwc) -{ - switch (hwc->config_base) { - case CPUMF_CTR_SET_BASIC: - case CPUMF_CTR_SET_USER: - case CPUMF_CTR_SET_CRYPTO: - case CPUMF_CTR_SET_EXT: - /* check for reserved counters */ - if ((hwc->config >= 6 && hwc->config <= 31) || - (hwc->config >= 38 && hwc->config <= 63) || - (hwc->config >= 80 && hwc->config <= 127)) - return -EOPNOTSUPP; - break; - default: - return -EINVAL; - } - - return 0; -} - -static int validate_ctr_version(const struct hw_perf_event *hwc) -{ - struct cpu_hw_events *cpuhw; - int err = 0; - - cpuhw = &get_cpu_var(cpu_hw_events); - - /* check required version for counter sets */ - switch (hwc->config_base) { - case CPUMF_CTR_SET_BASIC: - case CPUMF_CTR_SET_USER: - if (cpuhw->info.cfvn < 1) - err = -EOPNOTSUPP; - break; - case CPUMF_CTR_SET_CRYPTO: - case CPUMF_CTR_SET_EXT: - if (cpuhw->info.csvn < 1) - err = -EOPNOTSUPP; - break; - } - - put_cpu_var(cpu_hw_events); - return err; -} - -static int validate_ctr_auth(const struct hw_perf_event *hwc) -{ - struct cpu_hw_events *cpuhw; - u64 ctrs_state; - int err = 0; - - cpuhw = &get_cpu_var(cpu_hw_events); - - /* check authorization for cpu counter sets */ - ctrs_state = cpumf_state_ctl[hwc->config_base]; - if (!(ctrs_state & cpuhw->info.auth_ctl)) - err = -EPERM; - - put_cpu_var(cpu_hw_events); - return err; -} - -/* - * Change the CPUMF state to active. - * Enable and activate the CPU-counter sets according - * to the per-cpu control state. - */ -static void cpumf_pmu_enable(struct pmu *pmu) -{ - struct cpu_hw_events *cpuhw = &__get_cpu_var(cpu_hw_events); - int err; - - if (cpuhw->flags & PMU_F_ENABLED) - return; - - err = lcctl(cpuhw->state); - if (err) { - pr_err("Enabling the performance measuring unit " - "failed with rc=%x\n", err); - return; - } - - cpuhw->flags |= PMU_F_ENABLED; -} - -/* - * Change the CPUMF state to inactive. - * Disable and enable (inactive) the CPU-counter sets according - * to the per-cpu control state. - */ -static void cpumf_pmu_disable(struct pmu *pmu) -{ - struct cpu_hw_events *cpuhw = &__get_cpu_var(cpu_hw_events); - int err; - u64 inactive; - - if (!(cpuhw->flags & PMU_F_ENABLED)) - return; - - inactive = cpuhw->state & ~((1 << CPUMF_LCCTL_ENABLE_SHIFT) - 1); - err = lcctl(inactive); - if (err) { - pr_err("Disabling the performance measuring unit " - "failed with rc=%x\n", err); - return; - } - - cpuhw->flags &= ~PMU_F_ENABLED; -} - - -/* Number of perf events counting hardware events */ -static atomic_t num_events = ATOMIC_INIT(0); -/* Used to avoid races in calling reserve/release_cpumf_hardware */ -static DEFINE_MUTEX(pmc_reserve_mutex); - -/* CPU-measurement alerts for the counter facility */ -static void cpumf_measurement_alert(struct ext_code ext_code, - unsigned int alert, unsigned long unused) -{ - struct cpu_hw_events *cpuhw; - - if (!(alert & CPU_MF_INT_CF_MASK)) - return; - - kstat_cpu(smp_processor_id()).irqs[EXTINT_CPM]++; - cpuhw = &__get_cpu_var(cpu_hw_events); - - /* Measurement alerts are shared and might happen when the PMU - * is not reserved. Ignore these alerts in this case. */ - if (!(cpuhw->flags & PMU_F_RESERVED)) - return; - - /* counter authorization change alert */ - if (alert & CPU_MF_INT_CF_CACA) - qctri(&cpuhw->info); - - /* loss of counter data alert */ - if (alert & CPU_MF_INT_CF_LCDA) - pr_err("CPU[%i] Counter data was lost\n", smp_processor_id()); -} - -#define PMC_INIT 0 -#define PMC_RELEASE 1 -static void setup_pmc_cpu(void *flags) -{ - struct cpu_hw_events *cpuhw = &__get_cpu_var(cpu_hw_events); - - switch (*((int *) flags)) { - case PMC_INIT: - memset(&cpuhw->info, 0, sizeof(cpuhw->info)); - qctri(&cpuhw->info); - cpuhw->flags |= PMU_F_RESERVED; - break; - - case PMC_RELEASE: - cpuhw->flags &= ~PMU_F_RESERVED; - break; - } - - /* Disable CPU counter sets */ - lcctl(0); -} - -/* Initialize the CPU-measurement facility */ -static int reserve_pmc_hardware(void) -{ - int flags = PMC_INIT; - - on_each_cpu(setup_pmc_cpu, &flags, 1); - measurement_alert_subclass_register(); - - return 0; -} - -/* Release the CPU-measurement facility */ -static void release_pmc_hardware(void) -{ - int flags = PMC_RELEASE; - - on_each_cpu(setup_pmc_cpu, &flags, 1); - measurement_alert_subclass_unregister(); -} - -/* Release the PMU if event is the last perf event */ -static void hw_perf_event_destroy(struct perf_event *event) -{ - if (!atomic_add_unless(&num_events, -1, 1)) { - mutex_lock(&pmc_reserve_mutex); - if (atomic_dec_return(&num_events) == 0) - release_pmc_hardware(); - mutex_unlock(&pmc_reserve_mutex); - } -} - -/* CPUMF <-> perf event mappings for kernel+userspace (basic set) */ -static const int cpumf_generic_events_basic[] = { - [PERF_COUNT_HW_CPU_CYCLES] = 0, - [PERF_COUNT_HW_INSTRUCTIONS] = 1, - [PERF_COUNT_HW_CACHE_REFERENCES] = -1, - [PERF_COUNT_HW_CACHE_MISSES] = -1, - [PERF_COUNT_HW_BRANCH_INSTRUCTIONS] = -1, - [PERF_COUNT_HW_BRANCH_MISSES] = -1, - [PERF_COUNT_HW_BUS_CYCLES] = -1, -}; -/* CPUMF <-> perf event mappings for userspace (problem-state set) */ -static const int cpumf_generic_events_user[] = { - [PERF_COUNT_HW_CPU_CYCLES] = 32, - [PERF_COUNT_HW_INSTRUCTIONS] = 33, - [PERF_COUNT_HW_CACHE_REFERENCES] = -1, - [PERF_COUNT_HW_CACHE_MISSES] = -1, - [PERF_COUNT_HW_BRANCH_INSTRUCTIONS] = -1, - [PERF_COUNT_HW_BRANCH_MISSES] = -1, - [PERF_COUNT_HW_BUS_CYCLES] = -1, -}; - -static int __hw_perf_event_init(struct perf_event *event) -{ - struct perf_event_attr *attr = &event->attr; - struct hw_perf_event *hwc = &event->hw; - int err; - u64 ev; - - switch (attr->type) { - case PERF_TYPE_RAW: - /* Raw events are used to access counters directly, - * hence do not permit excludes */ - if (attr->exclude_kernel || attr->exclude_user || - attr->exclude_hv) - return -EOPNOTSUPP; - ev = attr->config; - break; - - case PERF_TYPE_HARDWARE: - ev = attr->config; - /* Count user space (problem-state) only */ - if (!attr->exclude_user && attr->exclude_kernel) { - if (ev >= ARRAY_SIZE(cpumf_generic_events_user)) - return -EOPNOTSUPP; - ev = cpumf_generic_events_user[ev]; - - /* No support for kernel space counters only */ - } else if (!attr->exclude_kernel && attr->exclude_user) { - return -EOPNOTSUPP; - - /* Count user and kernel space */ - } else { - if (ev >= ARRAY_SIZE(cpumf_generic_events_basic)) - return -EOPNOTSUPP; - ev = cpumf_generic_events_basic[ev]; - } - break; - - default: - return -ENOENT; - } - - if (ev == -1) - return -ENOENT; - - if (ev >= PERF_CPUM_CF_MAX_CTR) - return -EINVAL; - - /* The CPU measurement counter facility does not have any interrupts - * to do sampling. Sampling must be provided by external means, - * for example, by timers. - */ - if (hwc->sample_period) - return -EINVAL; - - /* Use the hardware perf event structure to store the counter number - * in 'config' member and the counter set to which the counter belongs - * in the 'config_base'. The counter set (config_base) is then used - * to enable/disable the counters. - */ - hwc->config = ev; - hwc->config_base = get_counter_set(ev); - - /* Validate the counter that is assigned to this event. - * Because the counter facility can use numerous counters at the - * same time without constraints, it is not necessary to explicity - * validate event groups (event->group_leader != event). - */ - err = validate_event(hwc); - if (err) - return err; - - /* Initialize for using the CPU-measurement counter facility */ - if (!atomic_inc_not_zero(&num_events)) { - mutex_lock(&pmc_reserve_mutex); - if (atomic_read(&num_events) == 0 && reserve_pmc_hardware()) - err = -EBUSY; - else - atomic_inc(&num_events); - mutex_unlock(&pmc_reserve_mutex); - } - event->destroy = hw_perf_event_destroy; - - /* Finally, validate version and authorization of the counter set */ - err = validate_ctr_auth(hwc); - if (!err) - err = validate_ctr_version(hwc); - - return err; -} - -static int cpumf_pmu_event_init(struct perf_event *event) -{ - int err; - - switch (event->attr.type) { - case PERF_TYPE_HARDWARE: - case PERF_TYPE_HW_CACHE: - case PERF_TYPE_RAW: - err = __hw_perf_event_init(event); - break; - default: - return -ENOENT; - } - - if (unlikely(err) && event->destroy) - event->destroy(event); - - return err; -} - -static int hw_perf_event_reset(struct perf_event *event) -{ - u64 prev, new; - int err; - - do { - prev = local64_read(&event->hw.prev_count); - err = ecctr(event->hw.config, &new); - if (err) { - if (err != 3) - break; - /* The counter is not (yet) available. This - * might happen if the counter set to which - * this counter belongs is in the disabled - * state. - */ - new = 0; - } - } while (local64_cmpxchg(&event->hw.prev_count, prev, new) != prev); - - return err; -} - -static int hw_perf_event_update(struct perf_event *event) -{ - u64 prev, new, delta; - int err; - - do { - prev = local64_read(&event->hw.prev_count); - err = ecctr(event->hw.config, &new); - if (err) - goto out; - } while (local64_cmpxchg(&event->hw.prev_count, prev, new) != prev); - - delta = (prev <= new) ? new - prev - : (-1ULL - prev) + new + 1; /* overflow */ - local64_add(delta, &event->count); -out: - return err; -} - -static void cpumf_pmu_read(struct perf_event *event) -{ - if (event->hw.state & PERF_HES_STOPPED) - return; - - hw_perf_event_update(event); -} - -static void cpumf_pmu_start(struct perf_event *event, int flags) -{ - struct cpu_hw_events *cpuhw = &__get_cpu_var(cpu_hw_events); - struct hw_perf_event *hwc = &event->hw; - - if (WARN_ON_ONCE(!(hwc->state & PERF_HES_STOPPED))) - return; - - if (WARN_ON_ONCE(hwc->config == -1)) - return; - - if (flags & PERF_EF_RELOAD) - WARN_ON_ONCE(!(hwc->state & PERF_HES_UPTODATE)); - - hwc->state = 0; - - /* (Re-)enable and activate the counter set */ - ctr_set_enable(&cpuhw->state, hwc->config_base); - ctr_set_start(&cpuhw->state, hwc->config_base); - - /* The counter set to which this counter belongs can be already active. - * Because all counters in a set are active, the event->hw.prev_count - * needs to be synchronized. At this point, the counter set can be in - * the inactive or disabled state. - */ - hw_perf_event_reset(event); - - /* increment refcount for this counter set */ - atomic_inc(&cpuhw->ctr_set[hwc->config_base]); -} - -static void cpumf_pmu_stop(struct perf_event *event, int flags) -{ - struct cpu_hw_events *cpuhw = &__get_cpu_var(cpu_hw_events); - struct hw_perf_event *hwc = &event->hw; - - if (!(hwc->state & PERF_HES_STOPPED)) { - /* Decrement reference count for this counter set and if this - * is the last used counter in the set, clear activation - * control and set the counter set state to inactive. - */ - if (!atomic_dec_return(&cpuhw->ctr_set[hwc->config_base])) - ctr_set_stop(&cpuhw->state, hwc->config_base); - event->hw.state |= PERF_HES_STOPPED; - } - - if ((flags & PERF_EF_UPDATE) && !(hwc->state & PERF_HES_UPTODATE)) { - hw_perf_event_update(event); - event->hw.state |= PERF_HES_UPTODATE; - } -} - -static int cpumf_pmu_add(struct perf_event *event, int flags) -{ - struct cpu_hw_events *cpuhw = &__get_cpu_var(cpu_hw_events); - - /* Check authorization for the counter set to which this - * counter belongs. - * For group events transaction, the authorization check is - * done in cpumf_pmu_commit_txn(). - */ - if (!(cpuhw->flags & PERF_EVENT_TXN)) - if (validate_ctr_auth(&event->hw)) - return -EPERM; - - ctr_set_enable(&cpuhw->state, event->hw.config_base); - event->hw.state = PERF_HES_UPTODATE | PERF_HES_STOPPED; - - if (flags & PERF_EF_START) - cpumf_pmu_start(event, PERF_EF_RELOAD); - - perf_event_update_userpage(event); - - return 0; -} - -static void cpumf_pmu_del(struct perf_event *event, int flags) -{ - struct cpu_hw_events *cpuhw = &__get_cpu_var(cpu_hw_events); - - cpumf_pmu_stop(event, PERF_EF_UPDATE); - - /* Check if any counter in the counter set is still used. If not used, - * change the counter set to the disabled state. This also clears the - * content of all counters in the set. - * - * When a new perf event has been added but not yet started, this can - * clear enable control and resets all counters in a set. Therefore, - * cpumf_pmu_start() always has to reenable a counter set. - */ - if (!atomic_read(&cpuhw->ctr_set[event->hw.config_base])) - ctr_set_disable(&cpuhw->state, event->hw.config_base); - - perf_event_update_userpage(event); -} - -/* - * Start group events scheduling transaction. - * Set flags to perform a single test at commit time. - */ -static void cpumf_pmu_start_txn(struct pmu *pmu) -{ - struct cpu_hw_events *cpuhw = &__get_cpu_var(cpu_hw_events); - - perf_pmu_disable(pmu); - cpuhw->flags |= PERF_EVENT_TXN; - cpuhw->tx_state = cpuhw->state; -} - -/* - * Stop and cancel a group events scheduling tranctions. - * Assumes cpumf_pmu_del() is called for each successful added - * cpumf_pmu_add() during the transaction. - */ -static void cpumf_pmu_cancel_txn(struct pmu *pmu) -{ - struct cpu_hw_events *cpuhw = &__get_cpu_var(cpu_hw_events); - - WARN_ON(cpuhw->tx_state != cpuhw->state); - - cpuhw->flags &= ~PERF_EVENT_TXN; - perf_pmu_enable(pmu); -} - -/* - * Commit the group events scheduling transaction. On success, the - * transaction is closed. On error, the transaction is kept open - * until cpumf_pmu_cancel_txn() is called. - */ -static int cpumf_pmu_commit_txn(struct pmu *pmu) -{ - struct cpu_hw_events *cpuhw = &__get_cpu_var(cpu_hw_events); - u64 state; - - /* check if the updated state can be scheduled */ - state = cpuhw->state & ~((1 << CPUMF_LCCTL_ENABLE_SHIFT) - 1); - state >>= CPUMF_LCCTL_ENABLE_SHIFT; - if ((state & cpuhw->info.auth_ctl) != state) - return -EPERM; - - cpuhw->flags &= ~PERF_EVENT_TXN; - perf_pmu_enable(pmu); - return 0; -} - -/* Performance monitoring unit for s390x */ -static struct pmu cpumf_pmu = { - .pmu_enable = cpumf_pmu_enable, - .pmu_disable = cpumf_pmu_disable, - .event_init = cpumf_pmu_event_init, - .add = cpumf_pmu_add, - .del = cpumf_pmu_del, - .start = cpumf_pmu_start, - .stop = cpumf_pmu_stop, - .read = cpumf_pmu_read, - .start_txn = cpumf_pmu_start_txn, - .commit_txn = cpumf_pmu_commit_txn, - .cancel_txn = cpumf_pmu_cancel_txn, -}; - -static int __cpuinit cpumf_pmu_notifier(struct notifier_block *self, - unsigned long action, void *hcpu) -{ - unsigned int cpu = (long) hcpu; - int flags; - - switch (action & ~CPU_TASKS_FROZEN) { - case CPU_ONLINE: - flags = PMC_INIT; - smp_call_function_single(cpu, setup_pmc_cpu, &flags, 1); - break; - case CPU_DOWN_PREPARE: - flags = PMC_RELEASE; - smp_call_function_single(cpu, setup_pmc_cpu, &flags, 1); - break; - default: - break; - } - - return NOTIFY_OK; -} - -static int __init cpumf_pmu_init(void) -{ - int rc; - - if (!cpum_cf_avail()) - return -ENODEV; - - /* clear bit 15 of cr0 to unauthorize problem-state to - * extract measurement counters */ - ctl_clear_bit(0, 48); - - /* register handler for measurement-alert interruptions */ - rc = register_external_interrupt(0x1407, cpumf_measurement_alert); - if (rc) { - pr_err("Registering for CPU-measurement alerts " - "failed with rc=%i\n", rc); - goto out; - } - - rc = perf_pmu_register(&cpumf_pmu, "cpum_cf", PERF_TYPE_RAW); - if (rc) { - pr_err("Registering the cpum_cf PMU failed with rc=%i\n", rc); - unregister_external_interrupt(0x1407, cpumf_measurement_alert); - goto out; - } - perf_cpu_notifier(cpumf_pmu_notifier); -out: - return rc; -} -early_initcall(cpumf_pmu_init); diff --git a/ANDROID_3.4.5/arch/s390/kernel/perf_event.c b/ANDROID_3.4.5/arch/s390/kernel/perf_event.c deleted file mode 100644 index f58f37f6..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/perf_event.c +++ /dev/null @@ -1,124 +0,0 @@ -/* - * Performance event support for s390x - * - * Copyright IBM Corp. 2012 - * Author(s): Hendrik Brueckner <brueckner@linux.vnet.ibm.com> - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License (version 2 only) - * as published by the Free Software Foundation. - */ -#define KMSG_COMPONENT "perf" -#define pr_fmt(fmt) KMSG_COMPONENT ": " fmt - -#include <linux/kernel.h> -#include <linux/perf_event.h> -#include <linux/percpu.h> -#include <linux/export.h> -#include <asm/irq.h> -#include <asm/cpu_mf.h> -#include <asm/lowcore.h> -#include <asm/processor.h> - -const char *perf_pmu_name(void) -{ - if (cpum_cf_avail() || cpum_sf_avail()) - return "CPU-measurement facilities (CPUMF)"; - return "pmu"; -} -EXPORT_SYMBOL(perf_pmu_name); - -int perf_num_counters(void) -{ - int num = 0; - - if (cpum_cf_avail()) - num += PERF_CPUM_CF_MAX_CTR; - - return num; -} -EXPORT_SYMBOL(perf_num_counters); - -void perf_event_print_debug(void) -{ - struct cpumf_ctr_info cf_info; - unsigned long flags; - int cpu; - - if (!cpum_cf_avail()) - return; - - local_irq_save(flags); - - cpu = smp_processor_id(); - memset(&cf_info, 0, sizeof(cf_info)); - if (!qctri(&cf_info)) { - pr_info("CPU[%i] CPUM_CF: ver=%u.%u A=%04x E=%04x C=%04x\n", - cpu, cf_info.cfvn, cf_info.csvn, - cf_info.auth_ctl, cf_info.enable_ctl, cf_info.act_ctl); - print_hex_dump_bytes("CPUMF Query: ", DUMP_PREFIX_OFFSET, - &cf_info, sizeof(cf_info)); - } - - local_irq_restore(flags); -} - -/* See also arch/s390/kernel/traps.c */ -static unsigned long __store_trace(struct perf_callchain_entry *entry, - unsigned long sp, - unsigned long low, unsigned long high) -{ - struct stack_frame *sf; - struct pt_regs *regs; - - while (1) { - sp = sp & PSW_ADDR_INSN; - if (sp < low || sp > high - sizeof(*sf)) - return sp; - sf = (struct stack_frame *) sp; - perf_callchain_store(entry, sf->gprs[8] & PSW_ADDR_INSN); - /* Follow the backchain. */ - while (1) { - low = sp; - sp = sf->back_chain & PSW_ADDR_INSN; - if (!sp) - break; - if (sp <= low || sp > high - sizeof(*sf)) - return sp; - sf = (struct stack_frame *) sp; - perf_callchain_store(entry, - sf->gprs[8] & PSW_ADDR_INSN); - } - /* Zero backchain detected, check for interrupt frame. */ - sp = (unsigned long) (sf + 1); - if (sp <= low || sp > high - sizeof(*regs)) - return sp; - regs = (struct pt_regs *) sp; - perf_callchain_store(entry, sf->gprs[8] & PSW_ADDR_INSN); - low = sp; - sp = regs->gprs[15]; - } -} - -void perf_callchain_kernel(struct perf_callchain_entry *entry, - struct pt_regs *regs) -{ - unsigned long head; - struct stack_frame *head_sf; - - if (user_mode(regs)) - return; - - head = regs->gprs[15]; - head_sf = (struct stack_frame *) head; - - if (!head_sf || !head_sf->back_chain) - return; - - head = head_sf->back_chain; - head = __store_trace(entry, head, S390_lowcore.async_stack - ASYNC_SIZE, - S390_lowcore.async_stack); - - __store_trace(entry, head, S390_lowcore.thread_info, - S390_lowcore.thread_info + THREAD_SIZE); -} diff --git a/ANDROID_3.4.5/arch/s390/kernel/process.c b/ANDROID_3.4.5/arch/s390/kernel/process.c deleted file mode 100644 index 60055cef..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/process.c +++ /dev/null @@ -1,354 +0,0 @@ -/* - * This file handles the architecture dependent parts of process handling. - * - * Copyright IBM Corp. 1999,2009 - * Author(s): Martin Schwidefsky <schwidefsky@de.ibm.com>, - * Hartmut Penner <hp@de.ibm.com>, - * Denis Joseph Barrow, - */ - -#include <linux/compiler.h> -#include <linux/cpu.h> -#include <linux/sched.h> -#include <linux/kernel.h> -#include <linux/mm.h> -#include <linux/elfcore.h> -#include <linux/smp.h> -#include <linux/slab.h> -#include <linux/interrupt.h> -#include <linux/tick.h> -#include <linux/personality.h> -#include <linux/syscalls.h> -#include <linux/compat.h> -#include <linux/kprobes.h> -#include <linux/random.h> -#include <linux/module.h> -#include <asm/io.h> -#include <asm/processor.h> -#include <asm/irq.h> -#include <asm/timer.h> -#include <asm/nmi.h> -#include <asm/smp.h> -#include <asm/switch_to.h> -#include "entry.h" - -asmlinkage void ret_from_fork(void) asm ("ret_from_fork"); - -/* - * Return saved PC of a blocked thread. used in kernel/sched. - * resume in entry.S does not create a new stack frame, it - * just stores the registers %r6-%r15 to the frame given by - * schedule. We want to return the address of the caller of - * schedule, so we have to walk the backchain one time to - * find the frame schedule() store its return address. - */ -unsigned long thread_saved_pc(struct task_struct *tsk) -{ - struct stack_frame *sf, *low, *high; - - if (!tsk || !task_stack_page(tsk)) - return 0; - low = task_stack_page(tsk); - high = (struct stack_frame *) task_pt_regs(tsk); - sf = (struct stack_frame *) (tsk->thread.ksp & PSW_ADDR_INSN); - if (sf <= low || sf > high) - return 0; - sf = (struct stack_frame *) (sf->back_chain & PSW_ADDR_INSN); - if (sf <= low || sf > high) - return 0; - return sf->gprs[8]; -} - -/* - * The idle loop on a S390... - */ -static void default_idle(void) -{ - if (cpu_is_offline(smp_processor_id())) - cpu_die(); - local_irq_disable(); - if (need_resched()) { - local_irq_enable(); - return; - } - local_mcck_disable(); - if (test_thread_flag(TIF_MCCK_PENDING)) { - local_mcck_enable(); - local_irq_enable(); - return; - } - /* Halt the cpu and keep track of cpu time accounting. */ - vtime_stop_cpu(); -} - -void cpu_idle(void) -{ - for (;;) { - tick_nohz_idle_enter(); - rcu_idle_enter(); - while (!need_resched() && !test_thread_flag(TIF_MCCK_PENDING)) - default_idle(); - rcu_idle_exit(); - tick_nohz_idle_exit(); - if (test_thread_flag(TIF_MCCK_PENDING)) - s390_handle_mcck(); - schedule_preempt_disabled(); - } -} - -extern void __kprobes kernel_thread_starter(void); - -asm( - ".section .kprobes.text, \"ax\"\n" - ".global kernel_thread_starter\n" - "kernel_thread_starter:\n" - " la 2,0(10)\n" - " basr 14,9\n" - " la 2,0\n" - " br 11\n" - ".previous\n"); - -int kernel_thread(int (*fn)(void *), void * arg, unsigned long flags) -{ - struct pt_regs regs; - - memset(®s, 0, sizeof(regs)); - regs.psw.mask = psw_kernel_bits | - PSW_MASK_DAT | PSW_MASK_IO | PSW_MASK_EXT | PSW_MASK_MCHECK; - regs.psw.addr = (unsigned long) kernel_thread_starter | PSW_ADDR_AMODE; - regs.gprs[9] = (unsigned long) fn; - regs.gprs[10] = (unsigned long) arg; - regs.gprs[11] = (unsigned long) do_exit; - regs.orig_gpr2 = -1; - - /* Ok, create the new process.. */ - return do_fork(flags | CLONE_VM | CLONE_UNTRACED, - 0, ®s, 0, NULL, NULL); -} -EXPORT_SYMBOL(kernel_thread); - -/* - * Free current thread data structures etc.. - */ -void exit_thread(void) -{ -} - -void flush_thread(void) -{ -} - -void release_thread(struct task_struct *dead_task) -{ -} - -int copy_thread(unsigned long clone_flags, unsigned long new_stackp, - unsigned long unused, - struct task_struct *p, struct pt_regs *regs) -{ - struct thread_info *ti; - struct fake_frame - { - struct stack_frame sf; - struct pt_regs childregs; - } *frame; - - frame = container_of(task_pt_regs(p), struct fake_frame, childregs); - p->thread.ksp = (unsigned long) frame; - /* Store access registers to kernel stack of new process. */ - frame->childregs = *regs; - frame->childregs.gprs[2] = 0; /* child returns 0 on fork. */ - frame->childregs.gprs[15] = new_stackp; - frame->sf.back_chain = 0; - - /* new return point is ret_from_fork */ - frame->sf.gprs[8] = (unsigned long) ret_from_fork; - - /* fake return stack for resume(), don't go back to schedule */ - frame->sf.gprs[9] = (unsigned long) frame; - - /* Save access registers to new thread structure. */ - save_access_regs(&p->thread.acrs[0]); - -#ifndef CONFIG_64BIT - /* - * save fprs to current->thread.fp_regs to merge them with - * the emulated registers and then copy the result to the child. - */ - save_fp_regs(¤t->thread.fp_regs); - memcpy(&p->thread.fp_regs, ¤t->thread.fp_regs, - sizeof(s390_fp_regs)); - /* Set a new TLS ? */ - if (clone_flags & CLONE_SETTLS) - p->thread.acrs[0] = regs->gprs[6]; -#else /* CONFIG_64BIT */ - /* Save the fpu registers to new thread structure. */ - save_fp_regs(&p->thread.fp_regs); - /* Set a new TLS ? */ - if (clone_flags & CLONE_SETTLS) { - if (is_compat_task()) { - p->thread.acrs[0] = (unsigned int) regs->gprs[6]; - } else { - p->thread.acrs[0] = (unsigned int)(regs->gprs[6] >> 32); - p->thread.acrs[1] = (unsigned int) regs->gprs[6]; - } - } -#endif /* CONFIG_64BIT */ - /* start new process with ar4 pointing to the correct address space */ - p->thread.mm_segment = get_fs(); - /* Don't copy debug registers */ - memset(&p->thread.per_user, 0, sizeof(p->thread.per_user)); - memset(&p->thread.per_event, 0, sizeof(p->thread.per_event)); - clear_tsk_thread_flag(p, TIF_SINGLE_STEP); - clear_tsk_thread_flag(p, TIF_PER_TRAP); - /* Initialize per thread user and system timer values */ - ti = task_thread_info(p); - ti->user_timer = 0; - ti->system_timer = 0; - return 0; -} - -SYSCALL_DEFINE0(fork) -{ - struct pt_regs *regs = task_pt_regs(current); - return do_fork(SIGCHLD, regs->gprs[15], regs, 0, NULL, NULL); -} - -SYSCALL_DEFINE4(clone, unsigned long, newsp, unsigned long, clone_flags, - int __user *, parent_tidptr, int __user *, child_tidptr) -{ - struct pt_regs *regs = task_pt_regs(current); - - if (!newsp) - newsp = regs->gprs[15]; - return do_fork(clone_flags, newsp, regs, 0, - parent_tidptr, child_tidptr); -} - -/* - * This is trivial, and on the face of it looks like it - * could equally well be done in user mode. - * - * Not so, for quite unobvious reasons - register pressure. - * In user mode vfork() cannot have a stack frame, and if - * done by calling the "clone()" system call directly, you - * do not have enough call-clobbered registers to hold all - * the information you need. - */ -SYSCALL_DEFINE0(vfork) -{ - struct pt_regs *regs = task_pt_regs(current); - return do_fork(CLONE_VFORK | CLONE_VM | SIGCHLD, - regs->gprs[15], regs, 0, NULL, NULL); -} - -asmlinkage void execve_tail(void) -{ - current->thread.fp_regs.fpc = 0; - if (MACHINE_HAS_IEEE) - asm volatile("sfpc %0,%0" : : "d" (0)); -} - -/* - * sys_execve() executes a new program. - */ -SYSCALL_DEFINE3(execve, const char __user *, name, - const char __user *const __user *, argv, - const char __user *const __user *, envp) -{ - struct pt_regs *regs = task_pt_regs(current); - char *filename; - long rc; - - filename = getname(name); - rc = PTR_ERR(filename); - if (IS_ERR(filename)) - return rc; - rc = do_execve(filename, argv, envp, regs); - if (rc) - goto out; - execve_tail(); - rc = regs->gprs[2]; -out: - putname(filename); - return rc; -} - -/* - * fill in the FPU structure for a core dump. - */ -int dump_fpu (struct pt_regs * regs, s390_fp_regs *fpregs) -{ -#ifndef CONFIG_64BIT - /* - * save fprs to current->thread.fp_regs to merge them with - * the emulated registers and then copy the result to the dump. - */ - save_fp_regs(¤t->thread.fp_regs); - memcpy(fpregs, ¤t->thread.fp_regs, sizeof(s390_fp_regs)); -#else /* CONFIG_64BIT */ - save_fp_regs(fpregs); -#endif /* CONFIG_64BIT */ - return 1; -} -EXPORT_SYMBOL(dump_fpu); - -unsigned long get_wchan(struct task_struct *p) -{ - struct stack_frame *sf, *low, *high; - unsigned long return_address; - int count; - - if (!p || p == current || p->state == TASK_RUNNING || !task_stack_page(p)) - return 0; - low = task_stack_page(p); - high = (struct stack_frame *) task_pt_regs(p); - sf = (struct stack_frame *) (p->thread.ksp & PSW_ADDR_INSN); - if (sf <= low || sf > high) - return 0; - for (count = 0; count < 16; count++) { - sf = (struct stack_frame *) (sf->back_chain & PSW_ADDR_INSN); - if (sf <= low || sf > high) - return 0; - return_address = sf->gprs[8] & PSW_ADDR_INSN; - if (!in_sched_functions(return_address)) - return return_address; - } - return 0; -} - -unsigned long arch_align_stack(unsigned long sp) -{ - if (!(current->personality & ADDR_NO_RANDOMIZE) && randomize_va_space) - sp -= get_random_int() & ~PAGE_MASK; - return sp & ~0xf; -} - -static inline unsigned long brk_rnd(void) -{ - /* 8MB for 32bit, 1GB for 64bit */ - if (is_32bit_task()) - return (get_random_int() & 0x7ffUL) << PAGE_SHIFT; - else - return (get_random_int() & 0x3ffffUL) << PAGE_SHIFT; -} - -unsigned long arch_randomize_brk(struct mm_struct *mm) -{ - unsigned long ret = PAGE_ALIGN(mm->brk + brk_rnd()); - - if (ret < mm->brk) - return mm->brk; - return ret; -} - -unsigned long randomize_et_dyn(unsigned long base) -{ - unsigned long ret = PAGE_ALIGN(base + brk_rnd()); - - if (!(current->flags & PF_RANDOMIZE)) - return base; - if (ret < base) - return base; - return ret; -} diff --git a/ANDROID_3.4.5/arch/s390/kernel/processor.c b/ANDROID_3.4.5/arch/s390/kernel/processor.c deleted file mode 100644 index 6e0073e4..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/processor.c +++ /dev/null @@ -1,96 +0,0 @@ -/* - * arch/s390/kernel/processor.c - * - * Copyright IBM Corp. 2008 - * Author(s): Martin Schwidefsky (schwidefsky@de.ibm.com) - */ - -#define KMSG_COMPONENT "cpu" -#define pr_fmt(fmt) KMSG_COMPONENT ": " fmt - -#include <linux/kernel.h> -#include <linux/init.h> -#include <linux/smp.h> -#include <linux/seq_file.h> -#include <linux/delay.h> -#include <linux/cpu.h> -#include <asm/elf.h> -#include <asm/lowcore.h> -#include <asm/param.h> - -static DEFINE_PER_CPU(struct cpuid, cpu_id); - -/* - * cpu_init - initializes state that is per-CPU. - */ -void __cpuinit cpu_init(void) -{ - struct cpuid *id = &per_cpu(cpu_id, smp_processor_id()); - - get_cpu_id(id); - atomic_inc(&init_mm.mm_count); - current->active_mm = &init_mm; - BUG_ON(current->mm); - enter_lazy_tlb(&init_mm, current); -} - -/* - * show_cpuinfo - Get information on one CPU for use by procfs. - */ -static int show_cpuinfo(struct seq_file *m, void *v) -{ - static const char *hwcap_str[10] = { - "esan3", "zarch", "stfle", "msa", "ldisp", "eimm", "dfp", - "edat", "etf3eh", "highgprs" - }; - unsigned long n = (unsigned long) v - 1; - int i; - - if (!n) { - s390_adjust_jiffies(); - seq_printf(m, "vendor_id : IBM/S390\n" - "# processors : %i\n" - "bogomips per cpu: %lu.%02lu\n", - num_online_cpus(), loops_per_jiffy/(500000/HZ), - (loops_per_jiffy/(5000/HZ))%100); - seq_puts(m, "features\t: "); - for (i = 0; i < 10; i++) - if (hwcap_str[i] && (elf_hwcap & (1UL << i))) - seq_printf(m, "%s ", hwcap_str[i]); - seq_puts(m, "\n"); - } - get_online_cpus(); - if (cpu_online(n)) { - struct cpuid *id = &per_cpu(cpu_id, n); - seq_printf(m, "processor %li: " - "version = %02X, " - "identification = %06X, " - "machine = %04X\n", - n, id->version, id->ident, id->machine); - } - put_online_cpus(); - return 0; -} - -static void *c_start(struct seq_file *m, loff_t *pos) -{ - return *pos < nr_cpu_ids ? (void *)((unsigned long) *pos + 1) : NULL; -} - -static void *c_next(struct seq_file *m, void *v, loff_t *pos) -{ - ++*pos; - return c_start(m, pos); -} - -static void c_stop(struct seq_file *m, void *v) -{ -} - -const struct seq_operations cpuinfo_op = { - .start = c_start, - .next = c_next, - .stop = c_stop, - .show = show_cpuinfo, -}; - diff --git a/ANDROID_3.4.5/arch/s390/kernel/ptrace.c b/ANDROID_3.4.5/arch/s390/kernel/ptrace.c deleted file mode 100644 index 02f300fb..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/ptrace.c +++ /dev/null @@ -1,1237 +0,0 @@ -/* - * Ptrace user space interface. - * - * Copyright IBM Corp. 1999,2010 - * Author(s): Denis Joseph Barrow - * Martin Schwidefsky (schwidefsky@de.ibm.com) - */ - -#include <linux/kernel.h> -#include <linux/sched.h> -#include <linux/mm.h> -#include <linux/smp.h> -#include <linux/errno.h> -#include <linux/ptrace.h> -#include <linux/user.h> -#include <linux/security.h> -#include <linux/audit.h> -#include <linux/signal.h> -#include <linux/elf.h> -#include <linux/regset.h> -#include <linux/tracehook.h> -#include <linux/seccomp.h> -#include <linux/compat.h> -#include <trace/syscall.h> -#include <asm/segment.h> -#include <asm/page.h> -#include <asm/pgtable.h> -#include <asm/pgalloc.h> -#include <asm/uaccess.h> -#include <asm/unistd.h> -#include <asm/switch_to.h> -#include "entry.h" - -#ifdef CONFIG_COMPAT -#include "compat_ptrace.h" -#endif - -#define CREATE_TRACE_POINTS -#include <trace/events/syscalls.h> - -enum s390_regset { - REGSET_GENERAL, - REGSET_FP, - REGSET_LAST_BREAK, - REGSET_SYSTEM_CALL, - REGSET_GENERAL_EXTENDED, -}; - -void update_per_regs(struct task_struct *task) -{ - struct pt_regs *regs = task_pt_regs(task); - struct thread_struct *thread = &task->thread; - struct per_regs old, new; - - /* Copy user specified PER registers */ - new.control = thread->per_user.control; - new.start = thread->per_user.start; - new.end = thread->per_user.end; - - /* merge TIF_SINGLE_STEP into user specified PER registers. */ - if (test_tsk_thread_flag(task, TIF_SINGLE_STEP)) { - new.control |= PER_EVENT_IFETCH; - new.start = 0; - new.end = PSW_ADDR_INSN; - } - - /* Take care of the PER enablement bit in the PSW. */ - if (!(new.control & PER_EVENT_MASK)) { - regs->psw.mask &= ~PSW_MASK_PER; - return; - } - regs->psw.mask |= PSW_MASK_PER; - __ctl_store(old, 9, 11); - if (memcmp(&new, &old, sizeof(struct per_regs)) != 0) - __ctl_load(new, 9, 11); -} - -void user_enable_single_step(struct task_struct *task) -{ - set_tsk_thread_flag(task, TIF_SINGLE_STEP); - if (task == current) - update_per_regs(task); -} - -void user_disable_single_step(struct task_struct *task) -{ - clear_tsk_thread_flag(task, TIF_SINGLE_STEP); - if (task == current) - update_per_regs(task); -} - -/* - * Called by kernel/ptrace.c when detaching.. - * - * Clear all debugging related fields. - */ -void ptrace_disable(struct task_struct *task) -{ - memset(&task->thread.per_user, 0, sizeof(task->thread.per_user)); - memset(&task->thread.per_event, 0, sizeof(task->thread.per_event)); - clear_tsk_thread_flag(task, TIF_SINGLE_STEP); - clear_tsk_thread_flag(task, TIF_PER_TRAP); -} - -#ifndef CONFIG_64BIT -# define __ADDR_MASK 3 -#else -# define __ADDR_MASK 7 -#endif - -static inline unsigned long __peek_user_per(struct task_struct *child, - addr_t addr) -{ - struct per_struct_kernel *dummy = NULL; - - if (addr == (addr_t) &dummy->cr9) - /* Control bits of the active per set. */ - return test_thread_flag(TIF_SINGLE_STEP) ? - PER_EVENT_IFETCH : child->thread.per_user.control; - else if (addr == (addr_t) &dummy->cr10) - /* Start address of the active per set. */ - return test_thread_flag(TIF_SINGLE_STEP) ? - 0 : child->thread.per_user.start; - else if (addr == (addr_t) &dummy->cr11) - /* End address of the active per set. */ - return test_thread_flag(TIF_SINGLE_STEP) ? - PSW_ADDR_INSN : child->thread.per_user.end; - else if (addr == (addr_t) &dummy->bits) - /* Single-step bit. */ - return test_thread_flag(TIF_SINGLE_STEP) ? - (1UL << (BITS_PER_LONG - 1)) : 0; - else if (addr == (addr_t) &dummy->starting_addr) - /* Start address of the user specified per set. */ - return child->thread.per_user.start; - else if (addr == (addr_t) &dummy->ending_addr) - /* End address of the user specified per set. */ - return child->thread.per_user.end; - else if (addr == (addr_t) &dummy->perc_atmid) - /* PER code, ATMID and AI of the last PER trap */ - return (unsigned long) - child->thread.per_event.cause << (BITS_PER_LONG - 16); - else if (addr == (addr_t) &dummy->address) - /* Address of the last PER trap */ - return child->thread.per_event.address; - else if (addr == (addr_t) &dummy->access_id) - /* Access id of the last PER trap */ - return (unsigned long) - child->thread.per_event.paid << (BITS_PER_LONG - 8); - return 0; -} - -/* - * Read the word at offset addr from the user area of a process. The - * trouble here is that the information is littered over different - * locations. The process registers are found on the kernel stack, - * the floating point stuff and the trace settings are stored in - * the task structure. In addition the different structures in - * struct user contain pad bytes that should be read as zeroes. - * Lovely... - */ -static unsigned long __peek_user(struct task_struct *child, addr_t addr) -{ - struct user *dummy = NULL; - addr_t offset, tmp; - - if (addr < (addr_t) &dummy->regs.acrs) { - /* - * psw and gprs are stored on the stack - */ - tmp = *(addr_t *)((addr_t) &task_pt_regs(child)->psw + addr); - if (addr == (addr_t) &dummy->regs.psw.mask) - /* Return a clean psw mask. */ - tmp = psw_user_bits | (tmp & PSW_MASK_USER); - - } else if (addr < (addr_t) &dummy->regs.orig_gpr2) { - /* - * access registers are stored in the thread structure - */ - offset = addr - (addr_t) &dummy->regs.acrs; -#ifdef CONFIG_64BIT - /* - * Very special case: old & broken 64 bit gdb reading - * from acrs[15]. Result is a 64 bit value. Read the - * 32 bit acrs[15] value and shift it by 32. Sick... - */ - if (addr == (addr_t) &dummy->regs.acrs[15]) - tmp = ((unsigned long) child->thread.acrs[15]) << 32; - else -#endif - tmp = *(addr_t *)((addr_t) &child->thread.acrs + offset); - - } else if (addr == (addr_t) &dummy->regs.orig_gpr2) { - /* - * orig_gpr2 is stored on the kernel stack - */ - tmp = (addr_t) task_pt_regs(child)->orig_gpr2; - - } else if (addr < (addr_t) &dummy->regs.fp_regs) { - /* - * prevent reads of padding hole between - * orig_gpr2 and fp_regs on s390. - */ - tmp = 0; - - } else if (addr < (addr_t) (&dummy->regs.fp_regs + 1)) { - /* - * floating point regs. are stored in the thread structure - */ - offset = addr - (addr_t) &dummy->regs.fp_regs; - tmp = *(addr_t *)((addr_t) &child->thread.fp_regs + offset); - if (addr == (addr_t) &dummy->regs.fp_regs.fpc) - tmp &= (unsigned long) FPC_VALID_MASK - << (BITS_PER_LONG - 32); - - } else if (addr < (addr_t) (&dummy->regs.per_info + 1)) { - /* - * Handle access to the per_info structure. - */ - addr -= (addr_t) &dummy->regs.per_info; - tmp = __peek_user_per(child, addr); - - } else - tmp = 0; - - return tmp; -} - -static int -peek_user(struct task_struct *child, addr_t addr, addr_t data) -{ - addr_t tmp, mask; - - /* - * Stupid gdb peeks/pokes the access registers in 64 bit with - * an alignment of 4. Programmers from hell... - */ - mask = __ADDR_MASK; -#ifdef CONFIG_64BIT - if (addr >= (addr_t) &((struct user *) NULL)->regs.acrs && - addr < (addr_t) &((struct user *) NULL)->regs.orig_gpr2) - mask = 3; -#endif - if ((addr & mask) || addr > sizeof(struct user) - __ADDR_MASK) - return -EIO; - - tmp = __peek_user(child, addr); - return put_user(tmp, (addr_t __user *) data); -} - -static inline void __poke_user_per(struct task_struct *child, - addr_t addr, addr_t data) -{ - struct per_struct_kernel *dummy = NULL; - - /* - * There are only three fields in the per_info struct that the - * debugger user can write to. - * 1) cr9: the debugger wants to set a new PER event mask - * 2) starting_addr: the debugger wants to set a new starting - * address to use with the PER event mask. - * 3) ending_addr: the debugger wants to set a new ending - * address to use with the PER event mask. - * The user specified PER event mask and the start and end - * addresses are used only if single stepping is not in effect. - * Writes to any other field in per_info are ignored. - */ - if (addr == (addr_t) &dummy->cr9) - /* PER event mask of the user specified per set. */ - child->thread.per_user.control = - data & (PER_EVENT_MASK | PER_CONTROL_MASK); - else if (addr == (addr_t) &dummy->starting_addr) - /* Starting address of the user specified per set. */ - child->thread.per_user.start = data; - else if (addr == (addr_t) &dummy->ending_addr) - /* Ending address of the user specified per set. */ - child->thread.per_user.end = data; -} - -/* - * Write a word to the user area of a process at location addr. This - * operation does have an additional problem compared to peek_user. - * Stores to the program status word and on the floating point - * control register needs to get checked for validity. - */ -static int __poke_user(struct task_struct *child, addr_t addr, addr_t data) -{ - struct user *dummy = NULL; - addr_t offset; - - if (addr < (addr_t) &dummy->regs.acrs) { - /* - * psw and gprs are stored on the stack - */ - if (addr == (addr_t) &dummy->regs.psw.mask && - ((data & ~PSW_MASK_USER) != psw_user_bits || - ((data & PSW_MASK_EA) && !(data & PSW_MASK_BA)))) - /* Invalid psw mask. */ - return -EINVAL; - *(addr_t *)((addr_t) &task_pt_regs(child)->psw + addr) = data; - - } else if (addr < (addr_t) (&dummy->regs.orig_gpr2)) { - /* - * access registers are stored in the thread structure - */ - offset = addr - (addr_t) &dummy->regs.acrs; -#ifdef CONFIG_64BIT - /* - * Very special case: old & broken 64 bit gdb writing - * to acrs[15] with a 64 bit value. Ignore the lower - * half of the value and write the upper 32 bit to - * acrs[15]. Sick... - */ - if (addr == (addr_t) &dummy->regs.acrs[15]) - child->thread.acrs[15] = (unsigned int) (data >> 32); - else -#endif - *(addr_t *)((addr_t) &child->thread.acrs + offset) = data; - - } else if (addr == (addr_t) &dummy->regs.orig_gpr2) { - /* - * orig_gpr2 is stored on the kernel stack - */ - task_pt_regs(child)->orig_gpr2 = data; - - } else if (addr < (addr_t) &dummy->regs.fp_regs) { - /* - * prevent writes of padding hole between - * orig_gpr2 and fp_regs on s390. - */ - return 0; - - } else if (addr < (addr_t) (&dummy->regs.fp_regs + 1)) { - /* - * floating point regs. are stored in the thread structure - */ - if (addr == (addr_t) &dummy->regs.fp_regs.fpc && - (data & ~((unsigned long) FPC_VALID_MASK - << (BITS_PER_LONG - 32))) != 0) - return -EINVAL; - offset = addr - (addr_t) &dummy->regs.fp_regs; - *(addr_t *)((addr_t) &child->thread.fp_regs + offset) = data; - - } else if (addr < (addr_t) (&dummy->regs.per_info + 1)) { - /* - * Handle access to the per_info structure. - */ - addr -= (addr_t) &dummy->regs.per_info; - __poke_user_per(child, addr, data); - - } - - return 0; -} - -static int poke_user(struct task_struct *child, addr_t addr, addr_t data) -{ - addr_t mask; - - /* - * Stupid gdb peeks/pokes the access registers in 64 bit with - * an alignment of 4. Programmers from hell indeed... - */ - mask = __ADDR_MASK; -#ifdef CONFIG_64BIT - if (addr >= (addr_t) &((struct user *) NULL)->regs.acrs && - addr < (addr_t) &((struct user *) NULL)->regs.orig_gpr2) - mask = 3; -#endif - if ((addr & mask) || addr > sizeof(struct user) - __ADDR_MASK) - return -EIO; - - return __poke_user(child, addr, data); -} - -long arch_ptrace(struct task_struct *child, long request, - unsigned long addr, unsigned long data) -{ - ptrace_area parea; - int copied, ret; - - switch (request) { - case PTRACE_PEEKUSR: - /* read the word at location addr in the USER area. */ - return peek_user(child, addr, data); - - case PTRACE_POKEUSR: - /* write the word at location addr in the USER area */ - return poke_user(child, addr, data); - - case PTRACE_PEEKUSR_AREA: - case PTRACE_POKEUSR_AREA: - if (copy_from_user(&parea, (void __force __user *) addr, - sizeof(parea))) - return -EFAULT; - addr = parea.kernel_addr; - data = parea.process_addr; - copied = 0; - while (copied < parea.len) { - if (request == PTRACE_PEEKUSR_AREA) - ret = peek_user(child, addr, data); - else { - addr_t utmp; - if (get_user(utmp, - (addr_t __force __user *) data)) - return -EFAULT; - ret = poke_user(child, addr, utmp); - } - if (ret) - return ret; - addr += sizeof(unsigned long); - data += sizeof(unsigned long); - copied += sizeof(unsigned long); - } - return 0; - case PTRACE_GET_LAST_BREAK: - put_user(task_thread_info(child)->last_break, - (unsigned long __user *) data); - return 0; - default: - /* Removing high order bit from addr (only for 31 bit). */ - addr &= PSW_ADDR_INSN; - return ptrace_request(child, request, addr, data); - } -} - -#ifdef CONFIG_COMPAT -/* - * Now the fun part starts... a 31 bit program running in the - * 31 bit emulation tracing another program. PTRACE_PEEKTEXT, - * PTRACE_PEEKDATA, PTRACE_POKETEXT and PTRACE_POKEDATA are easy - * to handle, the difference to the 64 bit versions of the requests - * is that the access is done in multiples of 4 byte instead of - * 8 bytes (sizeof(unsigned long) on 31/64 bit). - * The ugly part are PTRACE_PEEKUSR, PTRACE_PEEKUSR_AREA, - * PTRACE_POKEUSR and PTRACE_POKEUSR_AREA. If the traced program - * is a 31 bit program too, the content of struct user can be - * emulated. A 31 bit program peeking into the struct user of - * a 64 bit program is a no-no. - */ - -/* - * Same as peek_user_per but for a 31 bit program. - */ -static inline __u32 __peek_user_per_compat(struct task_struct *child, - addr_t addr) -{ - struct compat_per_struct_kernel *dummy32 = NULL; - - if (addr == (addr_t) &dummy32->cr9) - /* Control bits of the active per set. */ - return (__u32) test_thread_flag(TIF_SINGLE_STEP) ? - PER_EVENT_IFETCH : child->thread.per_user.control; - else if (addr == (addr_t) &dummy32->cr10) - /* Start address of the active per set. */ - return (__u32) test_thread_flag(TIF_SINGLE_STEP) ? - 0 : child->thread.per_user.start; - else if (addr == (addr_t) &dummy32->cr11) - /* End address of the active per set. */ - return test_thread_flag(TIF_SINGLE_STEP) ? - PSW32_ADDR_INSN : child->thread.per_user.end; - else if (addr == (addr_t) &dummy32->bits) - /* Single-step bit. */ - return (__u32) test_thread_flag(TIF_SINGLE_STEP) ? - 0x80000000 : 0; - else if (addr == (addr_t) &dummy32->starting_addr) - /* Start address of the user specified per set. */ - return (__u32) child->thread.per_user.start; - else if (addr == (addr_t) &dummy32->ending_addr) - /* End address of the user specified per set. */ - return (__u32) child->thread.per_user.end; - else if (addr == (addr_t) &dummy32->perc_atmid) - /* PER code, ATMID and AI of the last PER trap */ - return (__u32) child->thread.per_event.cause << 16; - else if (addr == (addr_t) &dummy32->address) - /* Address of the last PER trap */ - return (__u32) child->thread.per_event.address; - else if (addr == (addr_t) &dummy32->access_id) - /* Access id of the last PER trap */ - return (__u32) child->thread.per_event.paid << 24; - return 0; -} - -/* - * Same as peek_user but for a 31 bit program. - */ -static u32 __peek_user_compat(struct task_struct *child, addr_t addr) -{ - struct compat_user *dummy32 = NULL; - addr_t offset; - __u32 tmp; - - if (addr < (addr_t) &dummy32->regs.acrs) { - struct pt_regs *regs = task_pt_regs(child); - /* - * psw and gprs are stored on the stack - */ - if (addr == (addr_t) &dummy32->regs.psw.mask) { - /* Fake a 31 bit psw mask. */ - tmp = (__u32)(regs->psw.mask >> 32); - tmp = psw32_user_bits | (tmp & PSW32_MASK_USER); - } else if (addr == (addr_t) &dummy32->regs.psw.addr) { - /* Fake a 31 bit psw address. */ - tmp = (__u32) regs->psw.addr | - (__u32)(regs->psw.mask & PSW_MASK_BA); - } else { - /* gpr 0-15 */ - tmp = *(__u32 *)((addr_t) ®s->psw + addr*2 + 4); - } - } else if (addr < (addr_t) (&dummy32->regs.orig_gpr2)) { - /* - * access registers are stored in the thread structure - */ - offset = addr - (addr_t) &dummy32->regs.acrs; - tmp = *(__u32*)((addr_t) &child->thread.acrs + offset); - - } else if (addr == (addr_t) (&dummy32->regs.orig_gpr2)) { - /* - * orig_gpr2 is stored on the kernel stack - */ - tmp = *(__u32*)((addr_t) &task_pt_regs(child)->orig_gpr2 + 4); - - } else if (addr < (addr_t) &dummy32->regs.fp_regs) { - /* - * prevent reads of padding hole between - * orig_gpr2 and fp_regs on s390. - */ - tmp = 0; - - } else if (addr < (addr_t) (&dummy32->regs.fp_regs + 1)) { - /* - * floating point regs. are stored in the thread structure - */ - offset = addr - (addr_t) &dummy32->regs.fp_regs; - tmp = *(__u32 *)((addr_t) &child->thread.fp_regs + offset); - - } else if (addr < (addr_t) (&dummy32->regs.per_info + 1)) { - /* - * Handle access to the per_info structure. - */ - addr -= (addr_t) &dummy32->regs.per_info; - tmp = __peek_user_per_compat(child, addr); - - } else - tmp = 0; - - return tmp; -} - -static int peek_user_compat(struct task_struct *child, - addr_t addr, addr_t data) -{ - __u32 tmp; - - if (!is_compat_task() || (addr & 3) || addr > sizeof(struct user) - 3) - return -EIO; - - tmp = __peek_user_compat(child, addr); - return put_user(tmp, (__u32 __user *) data); -} - -/* - * Same as poke_user_per but for a 31 bit program. - */ -static inline void __poke_user_per_compat(struct task_struct *child, - addr_t addr, __u32 data) -{ - struct compat_per_struct_kernel *dummy32 = NULL; - - if (addr == (addr_t) &dummy32->cr9) - /* PER event mask of the user specified per set. */ - child->thread.per_user.control = - data & (PER_EVENT_MASK | PER_CONTROL_MASK); - else if (addr == (addr_t) &dummy32->starting_addr) - /* Starting address of the user specified per set. */ - child->thread.per_user.start = data; - else if (addr == (addr_t) &dummy32->ending_addr) - /* Ending address of the user specified per set. */ - child->thread.per_user.end = data; -} - -/* - * Same as poke_user but for a 31 bit program. - */ -static int __poke_user_compat(struct task_struct *child, - addr_t addr, addr_t data) -{ - struct compat_user *dummy32 = NULL; - __u32 tmp = (__u32) data; - addr_t offset; - - if (addr < (addr_t) &dummy32->regs.acrs) { - struct pt_regs *regs = task_pt_regs(child); - /* - * psw, gprs, acrs and orig_gpr2 are stored on the stack - */ - if (addr == (addr_t) &dummy32->regs.psw.mask) { - /* Build a 64 bit psw mask from 31 bit mask. */ - if ((tmp & ~PSW32_MASK_USER) != psw32_user_bits) - /* Invalid psw mask. */ - return -EINVAL; - regs->psw.mask = (regs->psw.mask & ~PSW_MASK_USER) | - (regs->psw.mask & PSW_MASK_BA) | - (__u64)(tmp & PSW32_MASK_USER) << 32; - } else if (addr == (addr_t) &dummy32->regs.psw.addr) { - /* Build a 64 bit psw address from 31 bit address. */ - regs->psw.addr = (__u64) tmp & PSW32_ADDR_INSN; - /* Transfer 31 bit amode bit to psw mask. */ - regs->psw.mask = (regs->psw.mask & ~PSW_MASK_BA) | - (__u64)(tmp & PSW32_ADDR_AMODE); - } else { - /* gpr 0-15 */ - *(__u32*)((addr_t) ®s->psw + addr*2 + 4) = tmp; - } - } else if (addr < (addr_t) (&dummy32->regs.orig_gpr2)) { - /* - * access registers are stored in the thread structure - */ - offset = addr - (addr_t) &dummy32->regs.acrs; - *(__u32*)((addr_t) &child->thread.acrs + offset) = tmp; - - } else if (addr == (addr_t) (&dummy32->regs.orig_gpr2)) { - /* - * orig_gpr2 is stored on the kernel stack - */ - *(__u32*)((addr_t) &task_pt_regs(child)->orig_gpr2 + 4) = tmp; - - } else if (addr < (addr_t) &dummy32->regs.fp_regs) { - /* - * prevent writess of padding hole between - * orig_gpr2 and fp_regs on s390. - */ - return 0; - - } else if (addr < (addr_t) (&dummy32->regs.fp_regs + 1)) { - /* - * floating point regs. are stored in the thread structure - */ - if (addr == (addr_t) &dummy32->regs.fp_regs.fpc && - (tmp & ~FPC_VALID_MASK) != 0) - /* Invalid floating point control. */ - return -EINVAL; - offset = addr - (addr_t) &dummy32->regs.fp_regs; - *(__u32 *)((addr_t) &child->thread.fp_regs + offset) = tmp; - - } else if (addr < (addr_t) (&dummy32->regs.per_info + 1)) { - /* - * Handle access to the per_info structure. - */ - addr -= (addr_t) &dummy32->regs.per_info; - __poke_user_per_compat(child, addr, data); - } - - return 0; -} - -static int poke_user_compat(struct task_struct *child, - addr_t addr, addr_t data) -{ - if (!is_compat_task() || (addr & 3) || - addr > sizeof(struct compat_user) - 3) - return -EIO; - - return __poke_user_compat(child, addr, data); -} - -long compat_arch_ptrace(struct task_struct *child, compat_long_t request, - compat_ulong_t caddr, compat_ulong_t cdata) -{ - unsigned long addr = caddr; - unsigned long data = cdata; - compat_ptrace_area parea; - int copied, ret; - - switch (request) { - case PTRACE_PEEKUSR: - /* read the word at location addr in the USER area. */ - return peek_user_compat(child, addr, data); - - case PTRACE_POKEUSR: - /* write the word at location addr in the USER area */ - return poke_user_compat(child, addr, data); - - case PTRACE_PEEKUSR_AREA: - case PTRACE_POKEUSR_AREA: - if (copy_from_user(&parea, (void __force __user *) addr, - sizeof(parea))) - return -EFAULT; - addr = parea.kernel_addr; - data = parea.process_addr; - copied = 0; - while (copied < parea.len) { - if (request == PTRACE_PEEKUSR_AREA) - ret = peek_user_compat(child, addr, data); - else { - __u32 utmp; - if (get_user(utmp, - (__u32 __force __user *) data)) - return -EFAULT; - ret = poke_user_compat(child, addr, utmp); - } - if (ret) - return ret; - addr += sizeof(unsigned int); - data += sizeof(unsigned int); - copied += sizeof(unsigned int); - } - return 0; - case PTRACE_GET_LAST_BREAK: - put_user(task_thread_info(child)->last_break, - (unsigned int __user *) data); - return 0; - } - return compat_ptrace_request(child, request, addr, data); -} -#endif - -asmlinkage long do_syscall_trace_enter(struct pt_regs *regs) -{ - long ret = 0; - - /* Do the secure computing check first. */ - secure_computing(regs->gprs[2]); - - /* - * The sysc_tracesys code in entry.S stored the system - * call number to gprs[2]. - */ - if (test_thread_flag(TIF_SYSCALL_TRACE) && - (tracehook_report_syscall_entry(regs) || - regs->gprs[2] >= NR_syscalls)) { - /* - * Tracing decided this syscall should not happen or the - * debugger stored an invalid system call number. Skip - * the system call and the system call restart handling. - */ - clear_thread_flag(TIF_SYSCALL); - ret = -1; - } - - if (unlikely(test_thread_flag(TIF_SYSCALL_TRACEPOINT))) - trace_sys_enter(regs, regs->gprs[2]); - - audit_syscall_entry(is_compat_task() ? - AUDIT_ARCH_S390 : AUDIT_ARCH_S390X, - regs->gprs[2], regs->orig_gpr2, - regs->gprs[3], regs->gprs[4], - regs->gprs[5]); - return ret ?: regs->gprs[2]; -} - -asmlinkage void do_syscall_trace_exit(struct pt_regs *regs) -{ - audit_syscall_exit(regs); - - if (unlikely(test_thread_flag(TIF_SYSCALL_TRACEPOINT))) - trace_sys_exit(regs, regs->gprs[2]); - - if (test_thread_flag(TIF_SYSCALL_TRACE)) - tracehook_report_syscall_exit(regs, 0); -} - -/* - * user_regset definitions. - */ - -static int s390_regs_get(struct task_struct *target, - const struct user_regset *regset, - unsigned int pos, unsigned int count, - void *kbuf, void __user *ubuf) -{ - if (target == current) - save_access_regs(target->thread.acrs); - - if (kbuf) { - unsigned long *k = kbuf; - while (count > 0) { - *k++ = __peek_user(target, pos); - count -= sizeof(*k); - pos += sizeof(*k); - } - } else { - unsigned long __user *u = ubuf; - while (count > 0) { - if (__put_user(__peek_user(target, pos), u++)) - return -EFAULT; - count -= sizeof(*u); - pos += sizeof(*u); - } - } - return 0; -} - -static int s390_regs_set(struct task_struct *target, - const struct user_regset *regset, - unsigned int pos, unsigned int count, - const void *kbuf, const void __user *ubuf) -{ - int rc = 0; - - if (target == current) - save_access_regs(target->thread.acrs); - - if (kbuf) { - const unsigned long *k = kbuf; - while (count > 0 && !rc) { - rc = __poke_user(target, pos, *k++); - count -= sizeof(*k); - pos += sizeof(*k); - } - } else { - const unsigned long __user *u = ubuf; - while (count > 0 && !rc) { - unsigned long word; - rc = __get_user(word, u++); - if (rc) - break; - rc = __poke_user(target, pos, word); - count -= sizeof(*u); - pos += sizeof(*u); - } - } - - if (rc == 0 && target == current) - restore_access_regs(target->thread.acrs); - - return rc; -} - -static int s390_fpregs_get(struct task_struct *target, - const struct user_regset *regset, unsigned int pos, - unsigned int count, void *kbuf, void __user *ubuf) -{ - if (target == current) - save_fp_regs(&target->thread.fp_regs); - - return user_regset_copyout(&pos, &count, &kbuf, &ubuf, - &target->thread.fp_regs, 0, -1); -} - -static int s390_fpregs_set(struct task_struct *target, - const struct user_regset *regset, unsigned int pos, - unsigned int count, const void *kbuf, - const void __user *ubuf) -{ - int rc = 0; - - if (target == current) - save_fp_regs(&target->thread.fp_regs); - - /* If setting FPC, must validate it first. */ - if (count > 0 && pos < offsetof(s390_fp_regs, fprs)) { - u32 fpc[2] = { target->thread.fp_regs.fpc, 0 }; - rc = user_regset_copyin(&pos, &count, &kbuf, &ubuf, &fpc, - 0, offsetof(s390_fp_regs, fprs)); - if (rc) - return rc; - if ((fpc[0] & ~FPC_VALID_MASK) != 0 || fpc[1] != 0) - return -EINVAL; - target->thread.fp_regs.fpc = fpc[0]; - } - - if (rc == 0 && count > 0) - rc = user_regset_copyin(&pos, &count, &kbuf, &ubuf, - target->thread.fp_regs.fprs, - offsetof(s390_fp_regs, fprs), -1); - - if (rc == 0 && target == current) - restore_fp_regs(&target->thread.fp_regs); - - return rc; -} - -#ifdef CONFIG_64BIT - -static int s390_last_break_get(struct task_struct *target, - const struct user_regset *regset, - unsigned int pos, unsigned int count, - void *kbuf, void __user *ubuf) -{ - if (count > 0) { - if (kbuf) { - unsigned long *k = kbuf; - *k = task_thread_info(target)->last_break; - } else { - unsigned long __user *u = ubuf; - if (__put_user(task_thread_info(target)->last_break, u)) - return -EFAULT; - } - } - return 0; -} - -static int s390_last_break_set(struct task_struct *target, - const struct user_regset *regset, - unsigned int pos, unsigned int count, - const void *kbuf, const void __user *ubuf) -{ - return 0; -} - -#endif - -static int s390_system_call_get(struct task_struct *target, - const struct user_regset *regset, - unsigned int pos, unsigned int count, - void *kbuf, void __user *ubuf) -{ - unsigned int *data = &task_thread_info(target)->system_call; - return user_regset_copyout(&pos, &count, &kbuf, &ubuf, - data, 0, sizeof(unsigned int)); -} - -static int s390_system_call_set(struct task_struct *target, - const struct user_regset *regset, - unsigned int pos, unsigned int count, - const void *kbuf, const void __user *ubuf) -{ - unsigned int *data = &task_thread_info(target)->system_call; - return user_regset_copyin(&pos, &count, &kbuf, &ubuf, - data, 0, sizeof(unsigned int)); -} - -static const struct user_regset s390_regsets[] = { - [REGSET_GENERAL] = { - .core_note_type = NT_PRSTATUS, - .n = sizeof(s390_regs) / sizeof(long), - .size = sizeof(long), - .align = sizeof(long), - .get = s390_regs_get, - .set = s390_regs_set, - }, - [REGSET_FP] = { - .core_note_type = NT_PRFPREG, - .n = sizeof(s390_fp_regs) / sizeof(long), - .size = sizeof(long), - .align = sizeof(long), - .get = s390_fpregs_get, - .set = s390_fpregs_set, - }, -#ifdef CONFIG_64BIT - [REGSET_LAST_BREAK] = { - .core_note_type = NT_S390_LAST_BREAK, - .n = 1, - .size = sizeof(long), - .align = sizeof(long), - .get = s390_last_break_get, - .set = s390_last_break_set, - }, -#endif - [REGSET_SYSTEM_CALL] = { - .core_note_type = NT_S390_SYSTEM_CALL, - .n = 1, - .size = sizeof(unsigned int), - .align = sizeof(unsigned int), - .get = s390_system_call_get, - .set = s390_system_call_set, - }, -}; - -static const struct user_regset_view user_s390_view = { - .name = UTS_MACHINE, - .e_machine = EM_S390, - .regsets = s390_regsets, - .n = ARRAY_SIZE(s390_regsets) -}; - -#ifdef CONFIG_COMPAT -static int s390_compat_regs_get(struct task_struct *target, - const struct user_regset *regset, - unsigned int pos, unsigned int count, - void *kbuf, void __user *ubuf) -{ - if (target == current) - save_access_regs(target->thread.acrs); - - if (kbuf) { - compat_ulong_t *k = kbuf; - while (count > 0) { - *k++ = __peek_user_compat(target, pos); - count -= sizeof(*k); - pos += sizeof(*k); - } - } else { - compat_ulong_t __user *u = ubuf; - while (count > 0) { - if (__put_user(__peek_user_compat(target, pos), u++)) - return -EFAULT; - count -= sizeof(*u); - pos += sizeof(*u); - } - } - return 0; -} - -static int s390_compat_regs_set(struct task_struct *target, - const struct user_regset *regset, - unsigned int pos, unsigned int count, - const void *kbuf, const void __user *ubuf) -{ - int rc = 0; - - if (target == current) - save_access_regs(target->thread.acrs); - - if (kbuf) { - const compat_ulong_t *k = kbuf; - while (count > 0 && !rc) { - rc = __poke_user_compat(target, pos, *k++); - count -= sizeof(*k); - pos += sizeof(*k); - } - } else { - const compat_ulong_t __user *u = ubuf; - while (count > 0 && !rc) { - compat_ulong_t word; - rc = __get_user(word, u++); - if (rc) - break; - rc = __poke_user_compat(target, pos, word); - count -= sizeof(*u); - pos += sizeof(*u); - } - } - - if (rc == 0 && target == current) - restore_access_regs(target->thread.acrs); - - return rc; -} - -static int s390_compat_regs_high_get(struct task_struct *target, - const struct user_regset *regset, - unsigned int pos, unsigned int count, - void *kbuf, void __user *ubuf) -{ - compat_ulong_t *gprs_high; - - gprs_high = (compat_ulong_t *) - &task_pt_regs(target)->gprs[pos / sizeof(compat_ulong_t)]; - if (kbuf) { - compat_ulong_t *k = kbuf; - while (count > 0) { - *k++ = *gprs_high; - gprs_high += 2; - count -= sizeof(*k); - } - } else { - compat_ulong_t __user *u = ubuf; - while (count > 0) { - if (__put_user(*gprs_high, u++)) - return -EFAULT; - gprs_high += 2; - count -= sizeof(*u); - } - } - return 0; -} - -static int s390_compat_regs_high_set(struct task_struct *target, - const struct user_regset *regset, - unsigned int pos, unsigned int count, - const void *kbuf, const void __user *ubuf) -{ - compat_ulong_t *gprs_high; - int rc = 0; - - gprs_high = (compat_ulong_t *) - &task_pt_regs(target)->gprs[pos / sizeof(compat_ulong_t)]; - if (kbuf) { - const compat_ulong_t *k = kbuf; - while (count > 0) { - *gprs_high = *k++; - *gprs_high += 2; - count -= sizeof(*k); - } - } else { - const compat_ulong_t __user *u = ubuf; - while (count > 0 && !rc) { - unsigned long word; - rc = __get_user(word, u++); - if (rc) - break; - *gprs_high = word; - *gprs_high += 2; - count -= sizeof(*u); - } - } - - return rc; -} - -static int s390_compat_last_break_get(struct task_struct *target, - const struct user_regset *regset, - unsigned int pos, unsigned int count, - void *kbuf, void __user *ubuf) -{ - compat_ulong_t last_break; - - if (count > 0) { - last_break = task_thread_info(target)->last_break; - if (kbuf) { - unsigned long *k = kbuf; - *k = last_break; - } else { - unsigned long __user *u = ubuf; - if (__put_user(last_break, u)) - return -EFAULT; - } - } - return 0; -} - -static int s390_compat_last_break_set(struct task_struct *target, - const struct user_regset *regset, - unsigned int pos, unsigned int count, - const void *kbuf, const void __user *ubuf) -{ - return 0; -} - -static const struct user_regset s390_compat_regsets[] = { - [REGSET_GENERAL] = { - .core_note_type = NT_PRSTATUS, - .n = sizeof(s390_compat_regs) / sizeof(compat_long_t), - .size = sizeof(compat_long_t), - .align = sizeof(compat_long_t), - .get = s390_compat_regs_get, - .set = s390_compat_regs_set, - }, - [REGSET_FP] = { - .core_note_type = NT_PRFPREG, - .n = sizeof(s390_fp_regs) / sizeof(compat_long_t), - .size = sizeof(compat_long_t), - .align = sizeof(compat_long_t), - .get = s390_fpregs_get, - .set = s390_fpregs_set, - }, - [REGSET_LAST_BREAK] = { - .core_note_type = NT_S390_LAST_BREAK, - .n = 1, - .size = sizeof(long), - .align = sizeof(long), - .get = s390_compat_last_break_get, - .set = s390_compat_last_break_set, - }, - [REGSET_SYSTEM_CALL] = { - .core_note_type = NT_S390_SYSTEM_CALL, - .n = 1, - .size = sizeof(compat_uint_t), - .align = sizeof(compat_uint_t), - .get = s390_system_call_get, - .set = s390_system_call_set, - }, - [REGSET_GENERAL_EXTENDED] = { - .core_note_type = NT_S390_HIGH_GPRS, - .n = sizeof(s390_compat_regs_high) / sizeof(compat_long_t), - .size = sizeof(compat_long_t), - .align = sizeof(compat_long_t), - .get = s390_compat_regs_high_get, - .set = s390_compat_regs_high_set, - }, -}; - -static const struct user_regset_view user_s390_compat_view = { - .name = "s390", - .e_machine = EM_S390, - .regsets = s390_compat_regsets, - .n = ARRAY_SIZE(s390_compat_regsets) -}; -#endif - -const struct user_regset_view *task_user_regset_view(struct task_struct *task) -{ -#ifdef CONFIG_COMPAT - if (test_tsk_thread_flag(task, TIF_31BIT)) - return &user_s390_compat_view; -#endif - return &user_s390_view; -} - -static const char *gpr_names[NUM_GPRS] = { - "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", - "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15", -}; - -unsigned long regs_get_register(struct pt_regs *regs, unsigned int offset) -{ - if (offset >= NUM_GPRS) - return 0; - return regs->gprs[offset]; -} - -int regs_query_register_offset(const char *name) -{ - unsigned long offset; - - if (!name || *name != 'r') - return -EINVAL; - if (strict_strtoul(name + 1, 10, &offset)) - return -EINVAL; - if (offset >= NUM_GPRS) - return -EINVAL; - return offset; -} - -const char *regs_query_register_name(unsigned int offset) -{ - if (offset >= NUM_GPRS) - return NULL; - return gpr_names[offset]; -} - -static int regs_within_kernel_stack(struct pt_regs *regs, unsigned long addr) -{ - unsigned long ksp = kernel_stack_pointer(regs); - - return (addr & ~(THREAD_SIZE - 1)) == (ksp & ~(THREAD_SIZE - 1)); -} - -/** - * regs_get_kernel_stack_nth() - get Nth entry of the stack - * @regs:pt_regs which contains kernel stack pointer. - * @n:stack entry number. - * - * regs_get_kernel_stack_nth() returns @n th entry of the kernel stack which - * is specifined by @regs. If the @n th entry is NOT in the kernel stack, - * this returns 0. - */ -unsigned long regs_get_kernel_stack_nth(struct pt_regs *regs, unsigned int n) -{ - unsigned long addr; - - addr = kernel_stack_pointer(regs) + n * sizeof(long); - if (!regs_within_kernel_stack(regs, addr)) - return 0; - return *(unsigned long *)addr; -} diff --git a/ANDROID_3.4.5/arch/s390/kernel/reipl.S b/ANDROID_3.4.5/arch/s390/kernel/reipl.S deleted file mode 100644 index ad67c214..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/reipl.S +++ /dev/null @@ -1,93 +0,0 @@ -/* - * arch/s390/kernel/reipl.S - * - * S390 version - * Copyright (C) 2000 IBM Deutschland Entwicklung GmbH, IBM Corporation - * Author(s): Holger Smolinski (Holger.Smolinski@de.ibm.com) - */ - -#include <linux/linkage.h> -#include <asm/asm-offsets.h> - -# -# store_status: Empty implementation until kdump is supported on 31 bit -# -ENTRY(store_status) - br %r14 - -# -# do_reipl_asm -# Parameter: r2 = schid of reipl device -# -ENTRY(do_reipl_asm) - basr %r13,0 -.Lpg0: lpsw .Lnewpsw-.Lpg0(%r13) -.Lpg1: # do store status of all registers - - stm %r0,%r15,__LC_GPREGS_SAVE_AREA - stctl %c0,%c15,__LC_CREGS_SAVE_AREA - stam %a0,%a15,__LC_AREGS_SAVE_AREA - l %r10,.Ldump_pfx-.Lpg0(%r13) - mvc __LC_PREFIX_SAVE_AREA(4),0(%r10) - stckc .Lclkcmp-.Lpg0(%r13) - mvc __LC_CLOCK_COMP_SAVE_AREA(8),.Lclkcmp-.Lpg0(%r13) - stpt __LC_CPU_TIMER_SAVE_AREA - st %r13, __LC_PSW_SAVE_AREA+4 - lctl %c6,%c6,.Lall-.Lpg0(%r13) - lr %r1,%r2 - mvc __LC_PGM_NEW_PSW(8),.Lpcnew-.Lpg0(%r13) - stsch .Lschib-.Lpg0(%r13) - oi .Lschib+5-.Lpg0(%r13),0x84 -.Lecs: xi .Lschib+27-.Lpg0(%r13),0x01 - msch .Lschib-.Lpg0(%r13) - lhi %r0,5 -.Lssch: ssch .Liplorb-.Lpg0(%r13) - jz .L001 - brct %r0,.Lssch - bas %r14,.Ldisab-.Lpg0(%r13) -.L001: mvc __LC_IO_NEW_PSW(8),.Lionew-.Lpg0(%r13) -.Ltpi: lpsw .Lwaitpsw-.Lpg0(%r13) -.Lcont: c %r1,__LC_SUBCHANNEL_ID - jnz .Ltpi - clc __LC_IO_INT_PARM(4),.Liplorb-.Lpg0(%r13) - jnz .Ltpi - tsch .Liplirb-.Lpg0(%r13) - tm .Liplirb+9-.Lpg0(%r13),0xbf - jz .L002 - bas %r14,.Ldisab-.Lpg0(%r13) -.L002: tm .Liplirb+8-.Lpg0(%r13),0xf3 - jz .L003 - bas %r14,.Ldisab-.Lpg0(%r13) -.L003: st %r1,__LC_SUBCHANNEL_ID - lpsw 0 - sigp 0,0,0(6) -.Ldisab: st %r14,.Ldispsw+4-.Lpg0(%r13) - lpsw .Ldispsw-.Lpg0(%r13) - .align 8 -.Lclkcmp: .quad 0x0000000000000000 -.Lall: .long 0xff000000 -.Ldump_pfx: .long dump_prefix_page - .align 8 -.Lnewpsw: .long 0x00080000,0x80000000+.Lpg1 -.Lpcnew: .long 0x00080000,0x80000000+.Lecs -.Lionew: .long 0x00080000,0x80000000+.Lcont -.Lwaitpsw: .long 0x020a0000,0x00000000+.Ltpi -.Ldispsw: .long 0x000a0000,0x00000000 -.Liplccws: .long 0x02000000,0x60000018 - .long 0x08000008,0x20000001 -.Liplorb: .long 0x0049504c,0x0040ff80 - .long 0x00000000+.Liplccws -.Lschib: .long 0x00000000,0x00000000 - .long 0x00000000,0x00000000 - .long 0x00000000,0x00000000 - .long 0x00000000,0x00000000 - .long 0x00000000,0x00000000 - .long 0x00000000,0x00000000 -.Liplirb: .long 0x00000000,0x00000000 - .long 0x00000000,0x00000000 - .long 0x00000000,0x00000000 - .long 0x00000000,0x00000000 - .long 0x00000000,0x00000000 - .long 0x00000000,0x00000000 - .long 0x00000000,0x00000000 - .long 0x00000000,0x00000000 diff --git a/ANDROID_3.4.5/arch/s390/kernel/reipl64.S b/ANDROID_3.4.5/arch/s390/kernel/reipl64.S deleted file mode 100644 index 36b32658..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/reipl64.S +++ /dev/null @@ -1,154 +0,0 @@ -/* - * Copyright IBM Corp 2000,2011 - * Author(s): Holger Smolinski <Holger.Smolinski@de.ibm.com>, - * Denis Joseph Barrow, - */ - -#include <linux/linkage.h> -#include <asm/asm-offsets.h> - -# -# store_status -# -# Prerequisites to run this function: -# - Prefix register is set to zero -# - Original prefix register is stored in "dump_prefix_page" -# - Lowcore protection is off -# -ENTRY(store_status) - /* Save register one and load save area base */ - stg %r1,__LC_SAVE_AREA_RESTART - lghi %r1,SAVE_AREA_BASE - /* General purpose registers */ - stmg %r0,%r15,__LC_GPREGS_SAVE_AREA-SAVE_AREA_BASE(%r1) - lg %r2,__LC_SAVE_AREA_RESTART - stg %r2,__LC_GPREGS_SAVE_AREA-SAVE_AREA_BASE+8(%r1) - /* Control registers */ - stctg %c0,%c15,__LC_CREGS_SAVE_AREA-SAVE_AREA_BASE(%r1) - /* Access registers */ - stam %a0,%a15,__LC_AREGS_SAVE_AREA-SAVE_AREA_BASE(%r1) - /* Floating point registers */ - std %f0, 0x00 + __LC_FPREGS_SAVE_AREA-SAVE_AREA_BASE(%r1) - std %f1, 0x08 + __LC_FPREGS_SAVE_AREA-SAVE_AREA_BASE(%r1) - std %f2, 0x10 + __LC_FPREGS_SAVE_AREA-SAVE_AREA_BASE(%r1) - std %f3, 0x18 + __LC_FPREGS_SAVE_AREA-SAVE_AREA_BASE(%r1) - std %f4, 0x20 + __LC_FPREGS_SAVE_AREA-SAVE_AREA_BASE(%r1) - std %f5, 0x28 + __LC_FPREGS_SAVE_AREA-SAVE_AREA_BASE(%r1) - std %f6, 0x30 + __LC_FPREGS_SAVE_AREA-SAVE_AREA_BASE(%r1) - std %f7, 0x38 + __LC_FPREGS_SAVE_AREA-SAVE_AREA_BASE(%r1) - std %f8, 0x40 + __LC_FPREGS_SAVE_AREA-SAVE_AREA_BASE(%r1) - std %f9, 0x48 + __LC_FPREGS_SAVE_AREA-SAVE_AREA_BASE(%r1) - std %f10,0x50 + __LC_FPREGS_SAVE_AREA-SAVE_AREA_BASE(%r1) - std %f11,0x58 + __LC_FPREGS_SAVE_AREA-SAVE_AREA_BASE(%r1) - std %f12,0x60 + __LC_FPREGS_SAVE_AREA-SAVE_AREA_BASE(%r1) - std %f13,0x68 + __LC_FPREGS_SAVE_AREA-SAVE_AREA_BASE(%r1) - std %f14,0x70 + __LC_FPREGS_SAVE_AREA-SAVE_AREA_BASE(%r1) - std %f15,0x78 + __LC_FPREGS_SAVE_AREA-SAVE_AREA_BASE(%r1) - /* Floating point control register */ - stfpc __LC_FP_CREG_SAVE_AREA-SAVE_AREA_BASE(%r1) - /* CPU timer */ - stpt __LC_CPU_TIMER_SAVE_AREA-SAVE_AREA_BASE(%r1) - /* Saved prefix register */ - larl %r2,dump_prefix_page - mvc __LC_PREFIX_SAVE_AREA-SAVE_AREA_BASE(4,%r1),0(%r2) - /* Clock comparator - seven bytes */ - larl %r2,.Lclkcmp - stckc 0(%r2) - mvc __LC_CLOCK_COMP_SAVE_AREA-SAVE_AREA_BASE + 1(7,%r1),1(%r2) - /* Program status word */ - epsw %r2,%r3 - st %r2,__LC_PSW_SAVE_AREA-SAVE_AREA_BASE + 0(%r1) - st %r3,__LC_PSW_SAVE_AREA-SAVE_AREA_BASE + 4(%r1) - larl %r2,store_status - stg %r2,__LC_PSW_SAVE_AREA-SAVE_AREA_BASE + 8(%r1) - br %r14 - - .section .bss - .align 8 -.Lclkcmp: .quad 0x0000000000000000 - .previous - -# -# do_reipl_asm -# Parameter: r2 = schid of reipl device -# - -ENTRY(do_reipl_asm) - basr %r13,0 -.Lpg0: lpswe .Lnewpsw-.Lpg0(%r13) -.Lpg1: brasl %r14,store_status - - lctlg %c6,%c6,.Lall-.Lpg0(%r13) - lgr %r1,%r2 - mvc __LC_PGM_NEW_PSW(16),.Lpcnew-.Lpg0(%r13) - stsch .Lschib-.Lpg0(%r13) - oi .Lschib+5-.Lpg0(%r13),0x84 -.Lecs: xi .Lschib+27-.Lpg0(%r13),0x01 - msch .Lschib-.Lpg0(%r13) - lghi %r0,5 -.Lssch: ssch .Liplorb-.Lpg0(%r13) - jz .L001 - brct %r0,.Lssch - bas %r14,.Ldisab-.Lpg0(%r13) -.L001: mvc __LC_IO_NEW_PSW(16),.Lionew-.Lpg0(%r13) -.Ltpi: lpswe .Lwaitpsw-.Lpg0(%r13) -.Lcont: c %r1,__LC_SUBCHANNEL_ID - jnz .Ltpi - clc __LC_IO_INT_PARM(4),.Liplorb-.Lpg0(%r13) - jnz .Ltpi - tsch .Liplirb-.Lpg0(%r13) - tm .Liplirb+9-.Lpg0(%r13),0xbf - jz .L002 - bas %r14,.Ldisab-.Lpg0(%r13) -.L002: tm .Liplirb+8-.Lpg0(%r13),0xf3 - jz .L003 - bas %r14,.Ldisab-.Lpg0(%r13) -.L003: st %r1,__LC_SUBCHANNEL_ID - lhi %r1,0 # mode 0 = esa - slr %r0,%r0 # set cpuid to zero - sigp %r1,%r0,0x12 # switch to esa mode - lpsw 0 -.Ldisab: sll %r14,1 - srl %r14,1 # need to kill hi bit to avoid specification exceptions. - st %r14,.Ldispsw+12-.Lpg0(%r13) - lpswe .Ldispsw-.Lpg0(%r13) - .align 8 -.Lall: .quad 0x00000000ff000000 - .align 16 -/* - * These addresses have to be 31 bit otherwise - * the sigp will throw a specifcation exception - * when switching to ESA mode as bit 31 be set - * in the ESA psw. - * Bit 31 of the addresses has to be 0 for the - * 31bit lpswe instruction a fact they appear to have - * omitted from the pop. - */ -.Lnewpsw: .quad 0x0000000080000000 - .quad .Lpg1 -.Lpcnew: .quad 0x0000000080000000 - .quad .Lecs -.Lionew: .quad 0x0000000080000000 - .quad .Lcont -.Lwaitpsw: .quad 0x0202000080000000 - .quad .Ltpi -.Ldispsw: .quad 0x0002000080000000 - .quad 0x0000000000000000 -.Liplccws: .long 0x02000000,0x60000018 - .long 0x08000008,0x20000001 -.Liplorb: .long 0x0049504c,0x0040ff80 - .long 0x00000000+.Liplccws -.Lschib: .long 0x00000000,0x00000000 - .long 0x00000000,0x00000000 - .long 0x00000000,0x00000000 - .long 0x00000000,0x00000000 - .long 0x00000000,0x00000000 - .long 0x00000000,0x00000000 -.Liplirb: .long 0x00000000,0x00000000 - .long 0x00000000,0x00000000 - .long 0x00000000,0x00000000 - .long 0x00000000,0x00000000 - .long 0x00000000,0x00000000 - .long 0x00000000,0x00000000 - .long 0x00000000,0x00000000 - .long 0x00000000,0x00000000 diff --git a/ANDROID_3.4.5/arch/s390/kernel/relocate_kernel.S b/ANDROID_3.4.5/arch/s390/kernel/relocate_kernel.S deleted file mode 100644 index c91d70ae..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/relocate_kernel.S +++ /dev/null @@ -1,119 +0,0 @@ -/* - * arch/s390/kernel/relocate_kernel.S - * - * (C) Copyright IBM Corp. 2005 - * - * Author(s): Rolf Adelsberger, - * Heiko Carstens <heiko.carstens@de.ibm.com> - * - */ - -#include <linux/linkage.h> - -/* - * moves the new kernel to its destination... - * %r2 = pointer to first kimage_entry_t - * %r3 = start address - where to jump to after the job is done... - * - * %r5 will be used as temp. storage - * %r6 holds the destination address - * %r7 = PAGE_SIZE - * %r8 holds the source address - * %r9 = PAGE_SIZE - * %r10 is a page mask - */ - - .text -ENTRY(relocate_kernel) - basr %r13,0 # base address - .base: - stnsm sys_msk-.base(%r13),0xfb # disable DAT - stctl %c0,%c15,ctlregs-.base(%r13) - stm %r0,%r15,gprregs-.base(%r13) - la %r1,load_psw-.base(%r13) - mvc 0(8,%r0),0(%r1) - la %r0,.back-.base(%r13) - st %r0,4(%r0) - oi 4(%r0),0x80 - mvc 0x68(8,%r0),0(%r1) - la %r0,.back_pgm-.base(%r13) - st %r0,0x6c(%r0) - oi 0x6c(%r0),0x80 - lhi %r0,0 - diag %r0,%r0,0x308 - .back: - basr %r13,0 - .back_base: - oi have_diag308-.back_base(%r13),0x01 - lctl %c0,%c15,ctlregs-.back_base(%r13) - lm %r0,%r15,gprregs-.back_base(%r13) - j .start_reloc - .back_pgm: - lm %r0,%r15,gprregs-.base(%r13) - .start_reloc: - lhi %r10,-1 # preparing the mask - sll %r10,12 # shift it such that it becomes 0xf000 - .top: - lhi %r7,4096 # load PAGE_SIZE in r7 - lhi %r9,4096 # load PAGE_SIZE in r9 - l %r5,0(%r2) # read another word for indirection page - ahi %r2,4 # increment pointer - tml %r5,0x1 # is it a destination page? - je .indir_check # NO, goto "indir_check" - lr %r6,%r5 # r6 = r5 - nr %r6,%r10 # mask it out and... - j .top # ...next iteration - .indir_check: - tml %r5,0x2 # is it a indirection page? - je .done_test # NO, goto "done_test" - nr %r5,%r10 # YES, mask out, - lr %r2,%r5 # move it into the right register, - j .top # and read next... - .done_test: - tml %r5,0x4 # is it the done indicator? - je .source_test # NO! Well, then it should be the source indicator... - j .done # ok, lets finish it here... - .source_test: - tml %r5,0x8 # it should be a source indicator... - je .top # NO, ignore it... - lr %r8,%r5 # r8 = r5 - nr %r8,%r10 # masking - 0: mvcle %r6,%r8,0x0 # copy PAGE_SIZE bytes from r8 to r6 - pad with 0 - jo 0b - j .top - .done: - sr %r0,%r0 # clear register r0 - la %r4,load_psw-.base(%r13) # load psw-address into the register - o %r3,4(%r4) # or load address into psw - st %r3,4(%r4) - mvc 0(8,%r0),0(%r4) # copy psw to absolute address 0 - tm have_diag308-.base(%r13),0x01 - jno .no_diag308 - diag %r0,%r0,0x308 - .no_diag308: - sr %r1,%r1 # clear %r1 - sr %r2,%r2 # clear %r2 - sigp %r1,%r2,0x12 # set cpuid to zero - lpsw 0 # hopefully start new kernel... - - .align 8 - load_psw: - .long 0x00080000,0x80000000 - sys_msk: - .quad 0 - ctlregs: - .rept 16 - .long 0 - .endr - gprregs: - .rept 16 - .long 0 - .endr - have_diag308: - .byte 0 - .align 8 - relocate_kernel_end: - .align 8 - .globl relocate_kernel_len - relocate_kernel_len: - .quad relocate_kernel_end - relocate_kernel diff --git a/ANDROID_3.4.5/arch/s390/kernel/relocate_kernel64.S b/ANDROID_3.4.5/arch/s390/kernel/relocate_kernel64.S deleted file mode 100644 index 7c3ce589..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/relocate_kernel64.S +++ /dev/null @@ -1,122 +0,0 @@ -/* - * arch/s390/kernel/relocate_kernel64.S - * - * (C) Copyright IBM Corp. 2005 - * - * Author(s): Rolf Adelsberger, - * Heiko Carstens <heiko.carstens@de.ibm.com> - * - */ - -#include <linux/linkage.h> - -/* - * moves the new kernel to its destination... - * %r2 = pointer to first kimage_entry_t - * %r3 = start address - where to jump to after the job is done... - * - * %r5 will be used as temp. storage - * %r6 holds the destination address - * %r7 = PAGE_SIZE - * %r8 holds the source address - * %r9 = PAGE_SIZE - * - * 0xf000 is a page_mask - */ - - .text -ENTRY(relocate_kernel) - basr %r13,0 # base address - .base: - stnsm sys_msk-.base(%r13),0xfb # disable DAT - stctg %c0,%c15,ctlregs-.base(%r13) - stmg %r0,%r15,gprregs-.base(%r13) - lghi %r0,3 - sllg %r0,%r0,31 - stg %r0,0x1d0(%r0) - la %r0,.back_pgm-.base(%r13) - stg %r0,0x1d8(%r0) - la %r1,load_psw-.base(%r13) - mvc 0(8,%r0),0(%r1) - la %r0,.back-.base(%r13) - st %r0,4(%r0) - oi 4(%r0),0x80 - lghi %r0,0 - diag %r0,%r0,0x308 - .back: - lhi %r1,1 # mode 1 = esame - sigp %r1,%r0,0x12 # switch to esame mode - sam64 # switch to 64 bit addressing mode - basr %r13,0 - .back_base: - oi have_diag308-.back_base(%r13),0x01 - lctlg %c0,%c15,ctlregs-.back_base(%r13) - lmg %r0,%r15,gprregs-.back_base(%r13) - j .top - .back_pgm: - lmg %r0,%r15,gprregs-.base(%r13) - .top: - lghi %r7,4096 # load PAGE_SIZE in r7 - lghi %r9,4096 # load PAGE_SIZE in r9 - lg %r5,0(%r2) # read another word for indirection page - aghi %r2,8 # increment pointer - tml %r5,0x1 # is it a destination page? - je .indir_check # NO, goto "indir_check" - lgr %r6,%r5 # r6 = r5 - nill %r6,0xf000 # mask it out and... - j .top # ...next iteration - .indir_check: - tml %r5,0x2 # is it a indirection page? - je .done_test # NO, goto "done_test" - nill %r5,0xf000 # YES, mask out, - lgr %r2,%r5 # move it into the right register, - j .top # and read next... - .done_test: - tml %r5,0x4 # is it the done indicator? - je .source_test # NO! Well, then it should be the source indicator... - j .done # ok, lets finish it here... - .source_test: - tml %r5,0x8 # it should be a source indicator... - je .top # NO, ignore it... - lgr %r8,%r5 # r8 = r5 - nill %r8,0xf000 # masking - 0: mvcle %r6,%r8,0x0 # copy PAGE_SIZE bytes from r8 to r6 - pad with 0 - jo 0b - j .top - .done: - sgr %r0,%r0 # clear register r0 - la %r4,load_psw-.base(%r13) # load psw-address into the register - o %r3,4(%r4) # or load address into psw - st %r3,4(%r4) - mvc 0(8,%r0),0(%r4) # copy psw to absolute address 0 - tm have_diag308-.base(%r13),0x01 - jno .no_diag308 - diag %r0,%r0,0x308 - .no_diag308: - sam31 # 31 bit mode - sr %r1,%r1 # erase register r1 - sr %r2,%r2 # erase register r2 - sigp %r1,%r2,0x12 # set cpuid to zero - lpsw 0 # hopefully start new kernel... - - .align 8 - load_psw: - .long 0x00080000,0x80000000 - sys_msk: - .quad 0 - ctlregs: - .rept 16 - .quad 0 - .endr - gprregs: - .rept 16 - .quad 0 - .endr - have_diag308: - .byte 0 - .align 8 - relocate_kernel_end: - .align 8 - .globl relocate_kernel_len - relocate_kernel_len: - .quad relocate_kernel_end - relocate_kernel diff --git a/ANDROID_3.4.5/arch/s390/kernel/s390_ksyms.c b/ANDROID_3.4.5/arch/s390/kernel/s390_ksyms.c deleted file mode 100644 index 57b53664..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/s390_ksyms.c +++ /dev/null @@ -1,10 +0,0 @@ -#include <linux/module.h> -#include <linux/kvm_host.h> -#include <asm/ftrace.h> - -#ifdef CONFIG_FUNCTION_TRACER -EXPORT_SYMBOL(_mcount); -#endif -#if defined(CONFIG_KVM) || defined(CONFIG_KVM_MODULE) -EXPORT_SYMBOL(sie64a); -#endif diff --git a/ANDROID_3.4.5/arch/s390/kernel/sclp.S b/ANDROID_3.4.5/arch/s390/kernel/sclp.S deleted file mode 100644 index 95792d84..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/sclp.S +++ /dev/null @@ -1,353 +0,0 @@ -/* - * Mini SCLP driver. - * - * Copyright IBM Corp. 2004,2009 - * - * Author(s): Peter Oberparleiter <Peter.Oberparleiter@de.ibm.com>, - * Heiko Carstens <heiko.carstens@de.ibm.com>, - * - */ - -#include <linux/linkage.h> - -LC_EXT_NEW_PSW = 0x58 # addr of ext int handler -LC_EXT_NEW_PSW_64 = 0x1b0 # addr of ext int handler 64 bit -LC_EXT_INT_PARAM = 0x80 # addr of ext int parameter -LC_EXT_INT_CODE = 0x86 # addr of ext int code -LC_AR_MODE_ID = 0xa3 - -# -# Subroutine which waits synchronously until either an external interruption -# or a timeout occurs. -# -# Parameters: -# R2 = 0 for no timeout, non-zero for timeout in (approximated) seconds -# -# Returns: -# R2 = 0 on interrupt, 2 on timeout -# R3 = external interruption parameter if R2=0 -# - -_sclp_wait_int: - stm %r6,%r15,24(%r15) # save registers - basr %r13,0 # get base register -.LbaseS1: - ahi %r15,-96 # create stack frame - la %r8,LC_EXT_NEW_PSW # register int handler - la %r9,.LextpswS1-.LbaseS1(%r13) -#ifdef CONFIG_64BIT - tm LC_AR_MODE_ID,1 - jno .Lesa1 - la %r8,LC_EXT_NEW_PSW_64 # register int handler 64 bit - la %r9,.LextpswS1_64-.LbaseS1(%r13) -.Lesa1: -#endif - mvc .LoldpswS1-.LbaseS1(16,%r13),0(%r8) - mvc 0(16,%r8),0(%r9) - lhi %r6,0x0200 # cr mask for ext int (cr0.54) - ltr %r2,%r2 - jz .LsetctS1 - ahi %r6,0x0800 # cr mask for clock int (cr0.52) - stck .LtimeS1-.LbaseS1(%r13) # initiate timeout - al %r2,.LtimeS1-.LbaseS1(%r13) - st %r2,.LtimeS1-.LbaseS1(%r13) - sckc .LtimeS1-.LbaseS1(%r13) - -.LsetctS1: - stctl %c0,%c0,.LctlS1-.LbaseS1(%r13) # enable required interrupts - l %r0,.LctlS1-.LbaseS1(%r13) - lhi %r1,~(0x200 | 0x800) # clear old values - nr %r1,%r0 - or %r1,%r6 # set new value - st %r1,.LctlS1-.LbaseS1(%r13) - lctl %c0,%c0,.LctlS1-.LbaseS1(%r13) - st %r0,.LctlS1-.LbaseS1(%r13) - lhi %r2,2 # return code for timeout -.LloopS1: - lpsw .LwaitpswS1-.LbaseS1(%r13) # wait until interrupt -.LwaitS1: - lh %r7,LC_EXT_INT_CODE - chi %r7,0x1004 # timeout? - je .LtimeoutS1 - chi %r7,0x2401 # service int? - jne .LloopS1 - sr %r2,%r2 - l %r3,LC_EXT_INT_PARAM -.LtimeoutS1: - lctl %c0,%c0,.LctlS1-.LbaseS1(%r13) # restore interrupt setting - # restore old handler - mvc 0(16,%r8),.LoldpswS1-.LbaseS1(%r13) - lm %r6,%r15,120(%r15) # restore registers - br %r14 # return to caller - - .align 8 -.LoldpswS1: - .long 0, 0, 0, 0 # old ext int PSW -.LextpswS1: - .long 0x00080000, 0x80000000+.LwaitS1 # PSW to handle ext int -#ifdef CONFIG_64BIT -.LextpswS1_64: - .quad 0x0000000180000000, .LwaitS1 # PSW to handle ext int, 64 bit -#endif -.LwaitpswS1: - .long 0x010a0000, 0x00000000+.LloopS1 # PSW to wait for ext int -.LtimeS1: - .quad 0 # current time -.LctlS1: - .long 0 # CT0 contents - -# -# Subroutine to synchronously issue a service call. -# -# Parameters: -# R2 = command word -# R3 = sccb address -# -# Returns: -# R2 = 0 on success, 1 on failure -# R3 = sccb response code if R2 = 0 -# - -_sclp_servc: - stm %r6,%r15,24(%r15) # save registers - ahi %r15,-96 # create stack frame - lr %r6,%r2 # save command word - lr %r7,%r3 # save sccb address -.LretryS2: - lhi %r2,1 # error return code - .insn rre,0xb2200000,%r6,%r7 # servc - brc 1,.LendS2 # exit if not operational - brc 8,.LnotbusyS2 # go on if not busy - sr %r2,%r2 # wait until no longer busy - bras %r14,_sclp_wait_int - j .LretryS2 # retry -.LnotbusyS2: - sr %r2,%r2 # wait until result - bras %r14,_sclp_wait_int - sr %r2,%r2 - lh %r3,6(%r7) -.LendS2: - lm %r6,%r15,120(%r15) # restore registers - br %r14 - -# -# Subroutine to set up the SCLP interface. -# -# Parameters: -# R2 = 0 to activate, non-zero to deactivate -# -# Returns: -# R2 = 0 on success, non-zero on failure -# - -_sclp_setup: - stm %r6,%r15,24(%r15) # save registers - ahi %r15,-96 # create stack frame - basr %r13,0 # get base register -.LbaseS3: - l %r6,.LsccbS0-.LbaseS3(%r13) # prepare init mask sccb - mvc 0(.LinitendS3-.LinitsccbS3,%r6),.LinitsccbS3-.LbaseS3(%r13) - ltr %r2,%r2 # initialization? - jz .LdoinitS3 # go ahead - # clear masks - xc .LinitmaskS3-.LinitsccbS3(8,%r6),.LinitmaskS3-.LinitsccbS3(%r6) -.LdoinitS3: - l %r2,.LwritemaskS3-.LbaseS3(%r13)# get command word - lr %r3,%r6 # get sccb address - bras %r14,_sclp_servc # issue service call - ltr %r2,%r2 # servc successful? - jnz .LerrorS3 - chi %r3,0x20 # write mask successful? - jne .LerrorS3 - # check masks - la %r2,.LinitmaskS3-.LinitsccbS3(%r6) - l %r1,0(%r2) # receive mask ok? - n %r1,12(%r2) - cl %r1,0(%r2) - jne .LerrorS3 - l %r1,4(%r2) # send mask ok? - n %r1,8(%r2) - cl %r1,4(%r2) - sr %r2,%r2 - je .LendS3 -.LerrorS3: - lhi %r2,1 # error return code -.LendS3: - lm %r6,%r15,120(%r15) # restore registers - br %r14 -.LwritemaskS3: - .long 0x00780005 # SCLP command for write mask -.LinitsccbS3: - .word .LinitendS3-.LinitsccbS3 - .byte 0,0,0,0 - .word 0 - .word 0 - .word 4 -.LinitmaskS3: - .long 0x80000000 - .long 0x40000000 - .long 0 - .long 0 -.LinitendS3: - -# -# Subroutine which prints a given text to the SCLP console. -# -# Parameters: -# R2 = address of nil-terminated ASCII text -# -# Returns: -# R2 = 0 on success, 1 on failure -# - -_sclp_print: - stm %r6,%r15,24(%r15) # save registers - ahi %r15,-96 # create stack frame - basr %r13,0 # get base register -.LbaseS4: - l %r8,.LsccbS0-.LbaseS4(%r13) # prepare write data sccb - mvc 0(.LmtoS4-.LwritesccbS4,%r8),.LwritesccbS4-.LbaseS4(%r13) - la %r7,.LmtoS4-.LwritesccbS4(%r8) # current mto addr - sr %r0,%r0 - l %r10,.Lascebc-.LbaseS4(%r13) # address of translation table -.LinitmtoS4: - # initialize mto - mvc 0(.LmtoendS4-.LmtoS4,%r7),.LmtoS4-.LbaseS4(%r13) - lhi %r6,.LmtoendS4-.LmtoS4 # current mto length -.LloopS4: - ic %r0,0(%r2) # get character - ahi %r2,1 - ltr %r0,%r0 # end of string? - jz .LfinalizemtoS4 - chi %r0,0x15 # end of line (NL)? - jz .LfinalizemtoS4 - stc %r0,0(%r6,%r7) # copy to mto - la %r11,0(%r6,%r7) - tr 0(1,%r11),0(%r10) # translate to EBCDIC - ahi %r6,1 - j .LloopS4 -.LfinalizemtoS4: - sth %r6,0(%r7) # update mto length - lh %r9,.LmdbS4-.LwritesccbS4(%r8) # update mdb length - ar %r9,%r6 - sth %r9,.LmdbS4-.LwritesccbS4(%r8) - lh %r9,.LevbufS4-.LwritesccbS4(%r8)# update evbuf length - ar %r9,%r6 - sth %r9,.LevbufS4-.LwritesccbS4(%r8) - lh %r9,0(%r8) # update sccb length - ar %r9,%r6 - sth %r9,0(%r8) - ar %r7,%r6 # update current mto address - ltr %r0,%r0 # more characters? - jnz .LinitmtoS4 - l %r2,.LwritedataS4-.LbaseS4(%r13)# write data - lr %r3,%r8 - bras %r14,_sclp_servc - ltr %r2,%r2 # servc successful? - jnz .LendS4 - chi %r3,0x20 # write data successful? - je .LendS4 - lhi %r2,1 # error return code -.LendS4: - lm %r6,%r15,120(%r15) # restore registers - br %r14 - -# -# Function which prints a given text to the SCLP console. -# -# Parameters: -# R2 = address of nil-terminated ASCII text -# -# Returns: -# R2 = 0 on success, 1 on failure -# - -ENTRY(_sclp_print_early) - stm %r6,%r15,24(%r15) # save registers - ahi %r15,-96 # create stack frame -#ifdef CONFIG_64BIT - tm LC_AR_MODE_ID,1 - jno .Lesa2 - ahi %r15,-80 - stmh %r6,%r15,96(%r15) # store upper register halves -.Lesa2: -#endif - lr %r10,%r2 # save string pointer - lhi %r2,0 - bras %r14,_sclp_setup # enable console - ltr %r2,%r2 - jnz .LendS5 - lr %r2,%r10 - bras %r14,_sclp_print # print string - ltr %r2,%r2 - jnz .LendS5 - lhi %r2,1 - bras %r14,_sclp_setup # disable console -.LendS5: -#ifdef CONFIG_64BIT - tm LC_AR_MODE_ID,1 - jno .Lesa3 - lmh %r6,%r15,96(%r15) # store upper register halves - ahi %r15,80 -.Lesa3: -#endif - lm %r6,%r15,120(%r15) # restore registers - br %r14 - -.LwritedataS4: - .long 0x00760005 # SCLP command for write data -.LwritesccbS4: - # sccb - .word .LmtoS4-.LwritesccbS4 - .byte 0 - .byte 0,0,0 - .word 0 - - # evbuf -.LevbufS4: - .word .LmtoS4-.LevbufS4 - .byte 0x02 - .byte 0 - .word 0 - -.LmdbS4: - # mdb - .word .LmtoS4-.LmdbS4 - .word 1 - .long 0xd4c4c240 - .long 1 - - # go -.LgoS4: - .word .LmtoS4-.LgoS4 - .word 1 - .long 0 - .byte 0,0,0,0,0,0,0,0 - .byte 0,0,0 - .byte 0 - .byte 0,0,0,0,0,0,0 - .byte 0 - .word 0 - .byte 0,0,0,0,0,0,0,0,0,0 - .byte 0,0,0,0,0,0,0,0 - .byte 0,0,0,0,0,0,0,0 - -.LmtoS4: - .word .LmtoendS4-.LmtoS4 - .word 4 - .word 0x1000 - .byte 0 - .byte 0,0,0 -.LmtoendS4: - - # Global constants -.LsccbS0: - .long _sclp_work_area -.Lascebc: - .long _ascebc - -.section .data,"aw",@progbits - .balign 4096 -_sclp_work_area: - .fill 4096 -.previous diff --git a/ANDROID_3.4.5/arch/s390/kernel/setup.c b/ANDROID_3.4.5/arch/s390/kernel/setup.c deleted file mode 100644 index 06264ae8..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/setup.c +++ /dev/null @@ -1,1092 +0,0 @@ -/* - * arch/s390/kernel/setup.c - * - * S390 version - * Copyright (C) IBM Corp. 1999,2012 - * Author(s): Hartmut Penner (hp@de.ibm.com), - * Martin Schwidefsky (schwidefsky@de.ibm.com) - * - * Derived from "arch/i386/kernel/setup.c" - * Copyright (C) 1995, Linus Torvalds - */ - -/* - * This file handles the architecture-dependent parts of initialization - */ - -#define KMSG_COMPONENT "setup" -#define pr_fmt(fmt) KMSG_COMPONENT ": " fmt - -#include <linux/errno.h> -#include <linux/module.h> -#include <linux/sched.h> -#include <linux/kernel.h> -#include <linux/memblock.h> -#include <linux/mm.h> -#include <linux/stddef.h> -#include <linux/unistd.h> -#include <linux/ptrace.h> -#include <linux/user.h> -#include <linux/tty.h> -#include <linux/ioport.h> -#include <linux/delay.h> -#include <linux/init.h> -#include <linux/initrd.h> -#include <linux/bootmem.h> -#include <linux/root_dev.h> -#include <linux/console.h> -#include <linux/kernel_stat.h> -#include <linux/device.h> -#include <linux/notifier.h> -#include <linux/pfn.h> -#include <linux/ctype.h> -#include <linux/reboot.h> -#include <linux/topology.h> -#include <linux/ftrace.h> -#include <linux/kexec.h> -#include <linux/crash_dump.h> -#include <linux/memory.h> -#include <linux/compat.h> - -#include <asm/ipl.h> -#include <asm/uaccess.h> -#include <asm/facility.h> -#include <asm/smp.h> -#include <asm/mmu_context.h> -#include <asm/cpcmd.h> -#include <asm/lowcore.h> -#include <asm/irq.h> -#include <asm/page.h> -#include <asm/ptrace.h> -#include <asm/sections.h> -#include <asm/ebcdic.h> -#include <asm/kvm_virtio.h> -#include <asm/diag.h> -#include <asm/os_info.h> -#include "entry.h" - -long psw_kernel_bits = PSW_DEFAULT_KEY | PSW_MASK_BASE | PSW_ASC_PRIMARY | - PSW_MASK_EA | PSW_MASK_BA; -long psw_user_bits = PSW_MASK_DAT | PSW_MASK_IO | PSW_MASK_EXT | - PSW_DEFAULT_KEY | PSW_MASK_BASE | PSW_MASK_MCHECK | - PSW_MASK_PSTATE | PSW_ASC_HOME; - -/* - * User copy operations. - */ -struct uaccess_ops uaccess; -EXPORT_SYMBOL(uaccess); - -/* - * Machine setup.. - */ -unsigned int console_mode = 0; -EXPORT_SYMBOL(console_mode); - -unsigned int console_devno = -1; -EXPORT_SYMBOL(console_devno); - -unsigned int console_irq = -1; -EXPORT_SYMBOL(console_irq); - -unsigned long elf_hwcap = 0; -char elf_platform[ELF_PLATFORM_SIZE]; - -struct mem_chunk __initdata memory_chunk[MEMORY_CHUNKS]; - -int __initdata memory_end_set; -unsigned long __initdata memory_end; - -unsigned long VMALLOC_START; -EXPORT_SYMBOL(VMALLOC_START); - -unsigned long VMALLOC_END; -EXPORT_SYMBOL(VMALLOC_END); - -struct page *vmemmap; -EXPORT_SYMBOL(vmemmap); - -/* An array with a pointer to the lowcore of every CPU. */ -struct _lowcore *lowcore_ptr[NR_CPUS]; -EXPORT_SYMBOL(lowcore_ptr); - -/* - * This is set up by the setup-routine at boot-time - * for S390 need to find out, what we have to setup - * using address 0x10400 ... - */ - -#include <asm/setup.h> - -/* - * condev= and conmode= setup parameter. - */ - -static int __init condev_setup(char *str) -{ - int vdev; - - vdev = simple_strtoul(str, &str, 0); - if (vdev >= 0 && vdev < 65536) { - console_devno = vdev; - console_irq = -1; - } - return 1; -} - -__setup("condev=", condev_setup); - -static void __init set_preferred_console(void) -{ - if (MACHINE_IS_KVM) - add_preferred_console("hvc", 0, NULL); - else if (CONSOLE_IS_3215 || CONSOLE_IS_SCLP) - add_preferred_console("ttyS", 0, NULL); - else if (CONSOLE_IS_3270) - add_preferred_console("tty3270", 0, NULL); -} - -static int __init conmode_setup(char *str) -{ -#if defined(CONFIG_SCLP_CONSOLE) || defined(CONFIG_SCLP_VT220_CONSOLE) - if (strncmp(str, "hwc", 4) == 0 || strncmp(str, "sclp", 5) == 0) - SET_CONSOLE_SCLP; -#endif -#if defined(CONFIG_TN3215_CONSOLE) - if (strncmp(str, "3215", 5) == 0) - SET_CONSOLE_3215; -#endif -#if defined(CONFIG_TN3270_CONSOLE) - if (strncmp(str, "3270", 5) == 0) - SET_CONSOLE_3270; -#endif - set_preferred_console(); - return 1; -} - -__setup("conmode=", conmode_setup); - -static void __init conmode_default(void) -{ - char query_buffer[1024]; - char *ptr; - - if (MACHINE_IS_VM) { - cpcmd("QUERY CONSOLE", query_buffer, 1024, NULL); - console_devno = simple_strtoul(query_buffer + 5, NULL, 16); - ptr = strstr(query_buffer, "SUBCHANNEL ="); - console_irq = simple_strtoul(ptr + 13, NULL, 16); - cpcmd("QUERY TERM", query_buffer, 1024, NULL); - ptr = strstr(query_buffer, "CONMODE"); - /* - * Set the conmode to 3215 so that the device recognition - * will set the cu_type of the console to 3215. If the - * conmode is 3270 and we don't set it back then both - * 3215 and the 3270 driver will try to access the console - * device (3215 as console and 3270 as normal tty). - */ - cpcmd("TERM CONMODE 3215", NULL, 0, NULL); - if (ptr == NULL) { -#if defined(CONFIG_SCLP_CONSOLE) || defined(CONFIG_SCLP_VT220_CONSOLE) - SET_CONSOLE_SCLP; -#endif - return; - } - if (strncmp(ptr + 8, "3270", 4) == 0) { -#if defined(CONFIG_TN3270_CONSOLE) - SET_CONSOLE_3270; -#elif defined(CONFIG_TN3215_CONSOLE) - SET_CONSOLE_3215; -#elif defined(CONFIG_SCLP_CONSOLE) || defined(CONFIG_SCLP_VT220_CONSOLE) - SET_CONSOLE_SCLP; -#endif - } else if (strncmp(ptr + 8, "3215", 4) == 0) { -#if defined(CONFIG_TN3215_CONSOLE) - SET_CONSOLE_3215; -#elif defined(CONFIG_TN3270_CONSOLE) - SET_CONSOLE_3270; -#elif defined(CONFIG_SCLP_CONSOLE) || defined(CONFIG_SCLP_VT220_CONSOLE) - SET_CONSOLE_SCLP; -#endif - } - } else { -#if defined(CONFIG_SCLP_CONSOLE) || defined(CONFIG_SCLP_VT220_CONSOLE) - SET_CONSOLE_SCLP; -#endif - } -} - -#ifdef CONFIG_ZFCPDUMP -static void __init setup_zfcpdump(unsigned int console_devno) -{ - static char str[41]; - - if (ipl_info.type != IPL_TYPE_FCP_DUMP) - return; - if (OLDMEM_BASE) - return; - if (console_devno != -1) - sprintf(str, " cio_ignore=all,!0.0.%04x,!0.0.%04x", - ipl_info.data.fcp.dev_id.devno, console_devno); - else - sprintf(str, " cio_ignore=all,!0.0.%04x", - ipl_info.data.fcp.dev_id.devno); - strcat(boot_command_line, str); - console_loglevel = 2; -} -#else -static inline void setup_zfcpdump(unsigned int console_devno) {} -#endif /* CONFIG_ZFCPDUMP */ - - /* - * Reboot, halt and power_off stubs. They just call _machine_restart, - * _machine_halt or _machine_power_off. - */ - -void machine_restart(char *command) -{ - if ((!in_interrupt() && !in_atomic()) || oops_in_progress) - /* - * Only unblank the console if we are called in enabled - * context or a bust_spinlocks cleared the way for us. - */ - console_unblank(); - _machine_restart(command); -} - -void machine_halt(void) -{ - if (!in_interrupt() || oops_in_progress) - /* - * Only unblank the console if we are called in enabled - * context or a bust_spinlocks cleared the way for us. - */ - console_unblank(); - _machine_halt(); -} - -void machine_power_off(void) -{ - if (!in_interrupt() || oops_in_progress) - /* - * Only unblank the console if we are called in enabled - * context or a bust_spinlocks cleared the way for us. - */ - console_unblank(); - _machine_power_off(); -} - -/* - * Dummy power off function. - */ -void (*pm_power_off)(void) = machine_power_off; - -static int __init early_parse_mem(char *p) -{ - memory_end = memparse(p, &p); - memory_end_set = 1; - return 0; -} -early_param("mem", early_parse_mem); - -static int __init parse_vmalloc(char *arg) -{ - if (!arg) - return -EINVAL; - VMALLOC_END = (memparse(arg, &arg) + PAGE_SIZE - 1) & PAGE_MASK; - return 0; -} -early_param("vmalloc", parse_vmalloc); - -unsigned int user_mode = HOME_SPACE_MODE; -EXPORT_SYMBOL_GPL(user_mode); - -static int set_amode_primary(void) -{ - psw_kernel_bits = (psw_kernel_bits & ~PSW_MASK_ASC) | PSW_ASC_HOME; - psw_user_bits = (psw_user_bits & ~PSW_MASK_ASC) | PSW_ASC_PRIMARY; -#ifdef CONFIG_COMPAT - psw32_user_bits = - (psw32_user_bits & ~PSW32_MASK_ASC) | PSW32_ASC_PRIMARY; -#endif - - if (MACHINE_HAS_MVCOS) { - memcpy(&uaccess, &uaccess_mvcos_switch, sizeof(uaccess)); - return 1; - } else { - memcpy(&uaccess, &uaccess_pt, sizeof(uaccess)); - return 0; - } -} - -/* - * Switch kernel/user addressing modes? - */ -static int __init early_parse_switch_amode(char *p) -{ - user_mode = PRIMARY_SPACE_MODE; - return 0; -} -early_param("switch_amode", early_parse_switch_amode); - -static int __init early_parse_user_mode(char *p) -{ - if (p && strcmp(p, "primary") == 0) - user_mode = PRIMARY_SPACE_MODE; - else if (!p || strcmp(p, "home") == 0) - user_mode = HOME_SPACE_MODE; - else - return 1; - return 0; -} -early_param("user_mode", early_parse_user_mode); - -static void setup_addressing_mode(void) -{ - if (user_mode == PRIMARY_SPACE_MODE) { - if (set_amode_primary()) - pr_info("Address spaces switched, " - "mvcos available\n"); - else - pr_info("Address spaces switched, " - "mvcos not available\n"); - } -} - -void *restart_stack __attribute__((__section__(".data"))); - -static void __init setup_lowcore(void) -{ - struct _lowcore *lc; - - /* - * Setup lowcore for boot cpu - */ - BUILD_BUG_ON(sizeof(struct _lowcore) != LC_PAGES * 4096); - lc = __alloc_bootmem_low(LC_PAGES * PAGE_SIZE, LC_PAGES * PAGE_SIZE, 0); - lc->restart_psw.mask = psw_kernel_bits; - lc->restart_psw.addr = - PSW_ADDR_AMODE | (unsigned long) restart_int_handler; - lc->external_new_psw.mask = psw_kernel_bits | - PSW_MASK_DAT | PSW_MASK_MCHECK; - lc->external_new_psw.addr = - PSW_ADDR_AMODE | (unsigned long) ext_int_handler; - lc->svc_new_psw.mask = psw_kernel_bits | - PSW_MASK_DAT | PSW_MASK_IO | PSW_MASK_EXT | PSW_MASK_MCHECK; - lc->svc_new_psw.addr = PSW_ADDR_AMODE | (unsigned long) system_call; - lc->program_new_psw.mask = psw_kernel_bits | - PSW_MASK_DAT | PSW_MASK_MCHECK; - lc->program_new_psw.addr = - PSW_ADDR_AMODE | (unsigned long) pgm_check_handler; - lc->mcck_new_psw.mask = psw_kernel_bits; - lc->mcck_new_psw.addr = - PSW_ADDR_AMODE | (unsigned long) mcck_int_handler; - lc->io_new_psw.mask = psw_kernel_bits | - PSW_MASK_DAT | PSW_MASK_MCHECK; - lc->io_new_psw.addr = PSW_ADDR_AMODE | (unsigned long) io_int_handler; - lc->clock_comparator = -1ULL; - lc->kernel_stack = ((unsigned long) &init_thread_union) + THREAD_SIZE; - lc->async_stack = (unsigned long) - __alloc_bootmem(ASYNC_SIZE, ASYNC_SIZE, 0) + ASYNC_SIZE; - lc->panic_stack = (unsigned long) - __alloc_bootmem(PAGE_SIZE, PAGE_SIZE, 0) + PAGE_SIZE; - lc->current_task = (unsigned long) init_thread_union.thread_info.task; - lc->thread_info = (unsigned long) &init_thread_union; - lc->machine_flags = S390_lowcore.machine_flags; - lc->stfl_fac_list = S390_lowcore.stfl_fac_list; - memcpy(lc->stfle_fac_list, S390_lowcore.stfle_fac_list, - MAX_FACILITY_BIT/8); -#ifndef CONFIG_64BIT - if (MACHINE_HAS_IEEE) { - lc->extended_save_area_addr = (__u32) - __alloc_bootmem_low(PAGE_SIZE, PAGE_SIZE, 0); - /* enable extended save area */ - __ctl_set_bit(14, 29); - } -#else - lc->vdso_per_cpu_data = (unsigned long) &lc->paste[0]; -#endif - lc->sync_enter_timer = S390_lowcore.sync_enter_timer; - lc->async_enter_timer = S390_lowcore.async_enter_timer; - lc->exit_timer = S390_lowcore.exit_timer; - lc->user_timer = S390_lowcore.user_timer; - lc->system_timer = S390_lowcore.system_timer; - lc->steal_timer = S390_lowcore.steal_timer; - lc->last_update_timer = S390_lowcore.last_update_timer; - lc->last_update_clock = S390_lowcore.last_update_clock; - lc->ftrace_func = S390_lowcore.ftrace_func; - - restart_stack = __alloc_bootmem(ASYNC_SIZE, ASYNC_SIZE, 0); - restart_stack += ASYNC_SIZE; - - /* - * Set up PSW restart to call ipl.c:do_restart(). Copy the relevant - * restart data to the absolute zero lowcore. This is necesary if - * PSW restart is done on an offline CPU that has lowcore zero. - */ - lc->restart_stack = (unsigned long) restart_stack; - lc->restart_fn = (unsigned long) do_restart; - lc->restart_data = 0; - lc->restart_source = -1UL; - memcpy(&S390_lowcore.restart_stack, &lc->restart_stack, - 4*sizeof(unsigned long)); - copy_to_absolute_zero(&S390_lowcore.restart_psw, - &lc->restart_psw, sizeof(psw_t)); - - set_prefix((u32)(unsigned long) lc); - lowcore_ptr[0] = lc; -} - -static struct resource code_resource = { - .name = "Kernel code", - .flags = IORESOURCE_BUSY | IORESOURCE_MEM, -}; - -static struct resource data_resource = { - .name = "Kernel data", - .flags = IORESOURCE_BUSY | IORESOURCE_MEM, -}; - -static struct resource bss_resource = { - .name = "Kernel bss", - .flags = IORESOURCE_BUSY | IORESOURCE_MEM, -}; - -static struct resource __initdata *standard_resources[] = { - &code_resource, - &data_resource, - &bss_resource, -}; - -static void __init setup_resources(void) -{ - struct resource *res, *std_res, *sub_res; - int i, j; - - code_resource.start = (unsigned long) &_text; - code_resource.end = (unsigned long) &_etext - 1; - data_resource.start = (unsigned long) &_etext; - data_resource.end = (unsigned long) &_edata - 1; - bss_resource.start = (unsigned long) &__bss_start; - bss_resource.end = (unsigned long) &__bss_stop - 1; - - for (i = 0; i < MEMORY_CHUNKS; i++) { - if (!memory_chunk[i].size) - continue; - if (memory_chunk[i].type == CHUNK_OLDMEM || - memory_chunk[i].type == CHUNK_CRASHK) - continue; - res = alloc_bootmem_low(sizeof(*res)); - res->flags = IORESOURCE_BUSY | IORESOURCE_MEM; - switch (memory_chunk[i].type) { - case CHUNK_READ_WRITE: - case CHUNK_CRASHK: - res->name = "System RAM"; - break; - case CHUNK_READ_ONLY: - res->name = "System ROM"; - res->flags |= IORESOURCE_READONLY; - break; - default: - res->name = "reserved"; - } - res->start = memory_chunk[i].addr; - res->end = res->start + memory_chunk[i].size - 1; - request_resource(&iomem_resource, res); - - for (j = 0; j < ARRAY_SIZE(standard_resources); j++) { - std_res = standard_resources[j]; - if (std_res->start < res->start || - std_res->start > res->end) - continue; - if (std_res->end > res->end) { - sub_res = alloc_bootmem_low(sizeof(*sub_res)); - *sub_res = *std_res; - sub_res->end = res->end; - std_res->start = res->end + 1; - request_resource(res, sub_res); - } else { - request_resource(res, std_res); - } - } - } -} - -unsigned long real_memory_size; -EXPORT_SYMBOL_GPL(real_memory_size); - -static void __init setup_memory_end(void) -{ - unsigned long vmax, vmalloc_size, tmp; - int i; - - -#ifdef CONFIG_ZFCPDUMP - if (ipl_info.type == IPL_TYPE_FCP_DUMP && !OLDMEM_BASE) { - memory_end = ZFCPDUMP_HSA_SIZE; - memory_end_set = 1; - } -#endif - real_memory_size = 0; - memory_end &= PAGE_MASK; - - /* - * Make sure all chunks are MAX_ORDER aligned so we don't need the - * extra checks that HOLES_IN_ZONE would require. - */ - for (i = 0; i < MEMORY_CHUNKS; i++) { - unsigned long start, end; - struct mem_chunk *chunk; - unsigned long align; - - chunk = &memory_chunk[i]; - align = 1UL << (MAX_ORDER + PAGE_SHIFT - 1); - start = (chunk->addr + align - 1) & ~(align - 1); - end = (chunk->addr + chunk->size) & ~(align - 1); - if (start >= end) - memset(chunk, 0, sizeof(*chunk)); - else { - chunk->addr = start; - chunk->size = end - start; - } - real_memory_size = max(real_memory_size, - chunk->addr + chunk->size); - } - - /* Choose kernel address space layout: 2, 3, or 4 levels. */ -#ifdef CONFIG_64BIT - vmalloc_size = VMALLOC_END ?: 128UL << 30; - tmp = (memory_end ?: real_memory_size) / PAGE_SIZE; - tmp = tmp * (sizeof(struct page) + PAGE_SIZE) + vmalloc_size; - if (tmp <= (1UL << 42)) - vmax = 1UL << 42; /* 3-level kernel page table */ - else - vmax = 1UL << 53; /* 4-level kernel page table */ -#else - vmalloc_size = VMALLOC_END ?: 96UL << 20; - vmax = 1UL << 31; /* 2-level kernel page table */ -#endif - /* vmalloc area is at the end of the kernel address space. */ - VMALLOC_END = vmax; - VMALLOC_START = vmax - vmalloc_size; - - /* Split remaining virtual space between 1:1 mapping & vmemmap array */ - tmp = VMALLOC_START / (PAGE_SIZE + sizeof(struct page)); - tmp = VMALLOC_START - tmp * sizeof(struct page); - tmp &= ~((vmax >> 11) - 1); /* align to page table level */ - tmp = min(tmp, 1UL << MAX_PHYSMEM_BITS); - vmemmap = (struct page *) tmp; - - /* Take care that memory_end is set and <= vmemmap */ - memory_end = min(memory_end ?: real_memory_size, tmp); - - /* Fixup memory chunk array to fit into 0..memory_end */ - for (i = 0; i < MEMORY_CHUNKS; i++) { - struct mem_chunk *chunk = &memory_chunk[i]; - - if (chunk->addr >= memory_end) { - memset(chunk, 0, sizeof(*chunk)); - continue; - } - if (chunk->addr + chunk->size > memory_end) - chunk->size = memory_end - chunk->addr; - } -} - -static void __init setup_vmcoreinfo(void) -{ -#ifdef CONFIG_KEXEC - unsigned long ptr = paddr_vmcoreinfo_note(); - - copy_to_absolute_zero(&S390_lowcore.vmcore_info, &ptr, sizeof(ptr)); -#endif -} - -#ifdef CONFIG_CRASH_DUMP - -/* - * Find suitable location for crashkernel memory - */ -static unsigned long __init find_crash_base(unsigned long crash_size, - char **msg) -{ - unsigned long crash_base; - struct mem_chunk *chunk; - int i; - - if (memory_chunk[0].size < crash_size) { - *msg = "first memory chunk must be at least crashkernel size"; - return 0; - } - if (OLDMEM_BASE && crash_size == OLDMEM_SIZE) - return OLDMEM_BASE; - - for (i = MEMORY_CHUNKS - 1; i >= 0; i--) { - chunk = &memory_chunk[i]; - if (chunk->size == 0) - continue; - if (chunk->type != CHUNK_READ_WRITE) - continue; - if (chunk->size < crash_size) - continue; - crash_base = (chunk->addr + chunk->size) - crash_size; - if (crash_base < crash_size) - continue; - if (crash_base < ZFCPDUMP_HSA_SIZE_MAX) - continue; - if (crash_base < (unsigned long) INITRD_START + INITRD_SIZE) - continue; - return crash_base; - } - *msg = "no suitable area found"; - return 0; -} - -/* - * Check if crash_base and crash_size is valid - */ -static int __init verify_crash_base(unsigned long crash_base, - unsigned long crash_size, - char **msg) -{ - struct mem_chunk *chunk; - int i; - - /* - * Because we do the swap to zero, we must have at least 'crash_size' - * bytes free space before crash_base - */ - if (crash_size > crash_base) { - *msg = "crashkernel offset must be greater than size"; - return -EINVAL; - } - - /* First memory chunk must be at least crash_size */ - if (memory_chunk[0].size < crash_size) { - *msg = "first memory chunk must be at least crashkernel size"; - return -EINVAL; - } - /* Check if we fit into the respective memory chunk */ - for (i = 0; i < MEMORY_CHUNKS; i++) { - chunk = &memory_chunk[i]; - if (chunk->size == 0) - continue; - if (crash_base < chunk->addr) - continue; - if (crash_base >= chunk->addr + chunk->size) - continue; - /* we have found the memory chunk */ - if (crash_base + crash_size > chunk->addr + chunk->size) { - *msg = "selected memory chunk is too small for " - "crashkernel memory"; - return -EINVAL; - } - return 0; - } - *msg = "invalid memory range specified"; - return -EINVAL; -} - -/* - * Reserve kdump memory by creating a memory hole in the mem_chunk array - */ -static void __init reserve_kdump_bootmem(unsigned long addr, unsigned long size, - int type) -{ - create_mem_hole(memory_chunk, addr, size, type); -} - -/* - * When kdump is enabled, we have to ensure that no memory from - * the area [0 - crashkernel memory size] and - * [crashk_res.start - crashk_res.end] is set offline. - */ -static int kdump_mem_notifier(struct notifier_block *nb, - unsigned long action, void *data) -{ - struct memory_notify *arg = data; - - if (arg->start_pfn < PFN_DOWN(resource_size(&crashk_res))) - return NOTIFY_BAD; - if (arg->start_pfn > PFN_DOWN(crashk_res.end)) - return NOTIFY_OK; - if (arg->start_pfn + arg->nr_pages - 1 < PFN_DOWN(crashk_res.start)) - return NOTIFY_OK; - return NOTIFY_BAD; -} - -static struct notifier_block kdump_mem_nb = { - .notifier_call = kdump_mem_notifier, -}; - -#endif - -/* - * Make sure that oldmem, where the dump is stored, is protected - */ -static void reserve_oldmem(void) -{ -#ifdef CONFIG_CRASH_DUMP - if (!OLDMEM_BASE) - return; - - reserve_kdump_bootmem(OLDMEM_BASE, OLDMEM_SIZE, CHUNK_OLDMEM); - reserve_kdump_bootmem(OLDMEM_SIZE, memory_end - OLDMEM_SIZE, - CHUNK_OLDMEM); - if (OLDMEM_BASE + OLDMEM_SIZE == real_memory_size) - saved_max_pfn = PFN_DOWN(OLDMEM_BASE) - 1; - else - saved_max_pfn = PFN_DOWN(real_memory_size) - 1; -#endif -} - -/* - * Reserve memory for kdump kernel to be loaded with kexec - */ -static void __init reserve_crashkernel(void) -{ -#ifdef CONFIG_CRASH_DUMP - unsigned long long crash_base, crash_size; - char *msg = NULL; - int rc; - - rc = parse_crashkernel(boot_command_line, memory_end, &crash_size, - &crash_base); - if (rc || crash_size == 0) - return; - crash_base = ALIGN(crash_base, KEXEC_CRASH_MEM_ALIGN); - crash_size = ALIGN(crash_size, KEXEC_CRASH_MEM_ALIGN); - if (register_memory_notifier(&kdump_mem_nb)) - return; - if (!crash_base) - crash_base = find_crash_base(crash_size, &msg); - if (!crash_base) { - pr_info("crashkernel reservation failed: %s\n", msg); - unregister_memory_notifier(&kdump_mem_nb); - return; - } - if (verify_crash_base(crash_base, crash_size, &msg)) { - pr_info("crashkernel reservation failed: %s\n", msg); - unregister_memory_notifier(&kdump_mem_nb); - return; - } - if (!OLDMEM_BASE && MACHINE_IS_VM) - diag10_range(PFN_DOWN(crash_base), PFN_DOWN(crash_size)); - crashk_res.start = crash_base; - crashk_res.end = crash_base + crash_size - 1; - insert_resource(&iomem_resource, &crashk_res); - reserve_kdump_bootmem(crash_base, crash_size, CHUNK_CRASHK); - pr_info("Reserving %lluMB of memory at %lluMB " - "for crashkernel (System RAM: %luMB)\n", - crash_size >> 20, crash_base >> 20, memory_end >> 20); - os_info_crashkernel_add(crash_base, crash_size); -#endif -} - -static void __init setup_memory(void) -{ - unsigned long bootmap_size; - unsigned long start_pfn, end_pfn; - int i; - - /* - * partially used pages are not usable - thus - * we are rounding upwards: - */ - start_pfn = PFN_UP(__pa(&_end)); - end_pfn = max_pfn = PFN_DOWN(memory_end); - -#ifdef CONFIG_BLK_DEV_INITRD - /* - * Move the initrd in case the bitmap of the bootmem allocater - * would overwrite it. - */ - - if (INITRD_START && INITRD_SIZE) { - unsigned long bmap_size; - unsigned long start; - - bmap_size = bootmem_bootmap_pages(end_pfn - start_pfn + 1); - bmap_size = PFN_PHYS(bmap_size); - - if (PFN_PHYS(start_pfn) + bmap_size > INITRD_START) { - start = PFN_PHYS(start_pfn) + bmap_size + PAGE_SIZE; - -#ifdef CONFIG_CRASH_DUMP - if (OLDMEM_BASE) { - /* Move initrd behind kdump oldmem */ - if (start + INITRD_SIZE > OLDMEM_BASE && - start < OLDMEM_BASE + OLDMEM_SIZE) - start = OLDMEM_BASE + OLDMEM_SIZE; - } -#endif - if (start + INITRD_SIZE > memory_end) { - pr_err("initrd extends beyond end of " - "memory (0x%08lx > 0x%08lx) " - "disabling initrd\n", - start + INITRD_SIZE, memory_end); - INITRD_START = INITRD_SIZE = 0; - } else { - pr_info("Moving initrd (0x%08lx -> " - "0x%08lx, size: %ld)\n", - INITRD_START, start, INITRD_SIZE); - memmove((void *) start, (void *) INITRD_START, - INITRD_SIZE); - INITRD_START = start; - } - } - } -#endif - - /* - * Initialize the boot-time allocator - */ - bootmap_size = init_bootmem(start_pfn, end_pfn); - - /* - * Register RAM areas with the bootmem allocator. - */ - - for (i = 0; i < MEMORY_CHUNKS && memory_chunk[i].size > 0; i++) { - unsigned long start_chunk, end_chunk, pfn; - - if (memory_chunk[i].type != CHUNK_READ_WRITE && - memory_chunk[i].type != CHUNK_CRASHK) - continue; - start_chunk = PFN_DOWN(memory_chunk[i].addr); - end_chunk = start_chunk + PFN_DOWN(memory_chunk[i].size); - end_chunk = min(end_chunk, end_pfn); - if (start_chunk >= end_chunk) - continue; - memblock_add_node(PFN_PHYS(start_chunk), - PFN_PHYS(end_chunk - start_chunk), 0); - pfn = max(start_chunk, start_pfn); - for (; pfn < end_chunk; pfn++) - page_set_storage_key(PFN_PHYS(pfn), - PAGE_DEFAULT_KEY, 0); - } - - psw_set_key(PAGE_DEFAULT_KEY); - - free_bootmem_with_active_regions(0, max_pfn); - - /* - * Reserve memory used for lowcore/command line/kernel image. - */ - reserve_bootmem(0, (unsigned long)_ehead, BOOTMEM_DEFAULT); - reserve_bootmem((unsigned long)_stext, - PFN_PHYS(start_pfn) - (unsigned long)_stext, - BOOTMEM_DEFAULT); - /* - * Reserve the bootmem bitmap itself as well. We do this in two - * steps (first step was init_bootmem()) because this catches - * the (very unlikely) case of us accidentally initializing the - * bootmem allocator with an invalid RAM area. - */ - reserve_bootmem(start_pfn << PAGE_SHIFT, bootmap_size, - BOOTMEM_DEFAULT); - -#ifdef CONFIG_CRASH_DUMP - if (crashk_res.start) - reserve_bootmem(crashk_res.start, - crashk_res.end - crashk_res.start + 1, - BOOTMEM_DEFAULT); - if (is_kdump_kernel()) - reserve_bootmem(elfcorehdr_addr - OLDMEM_BASE, - PAGE_ALIGN(elfcorehdr_size), BOOTMEM_DEFAULT); -#endif -#ifdef CONFIG_BLK_DEV_INITRD - if (INITRD_START && INITRD_SIZE) { - if (INITRD_START + INITRD_SIZE <= memory_end) { - reserve_bootmem(INITRD_START, INITRD_SIZE, - BOOTMEM_DEFAULT); - initrd_start = INITRD_START; - initrd_end = initrd_start + INITRD_SIZE; - } else { - pr_err("initrd extends beyond end of " - "memory (0x%08lx > 0x%08lx) " - "disabling initrd\n", - initrd_start + INITRD_SIZE, memory_end); - initrd_start = initrd_end = 0; - } - } -#endif -} - -/* - * Setup hardware capabilities. - */ -static void __init setup_hwcaps(void) -{ - static const int stfl_bits[6] = { 0, 2, 7, 17, 19, 21 }; - struct cpuid cpu_id; - int i; - - /* - * The store facility list bits numbers as found in the principles - * of operation are numbered with bit 1UL<<31 as number 0 to - * bit 1UL<<0 as number 31. - * Bit 0: instructions named N3, "backported" to esa-mode - * Bit 2: z/Architecture mode is active - * Bit 7: the store-facility-list-extended facility is installed - * Bit 17: the message-security assist is installed - * Bit 19: the long-displacement facility is installed - * Bit 21: the extended-immediate facility is installed - * Bit 22: extended-translation facility 3 is installed - * Bit 30: extended-translation facility 3 enhancement facility - * These get translated to: - * HWCAP_S390_ESAN3 bit 0, HWCAP_S390_ZARCH bit 1, - * HWCAP_S390_STFLE bit 2, HWCAP_S390_MSA bit 3, - * HWCAP_S390_LDISP bit 4, HWCAP_S390_EIMM bit 5 and - * HWCAP_S390_ETF3EH bit 8 (22 && 30). - */ - for (i = 0; i < 6; i++) - if (test_facility(stfl_bits[i])) - elf_hwcap |= 1UL << i; - - if (test_facility(22) && test_facility(30)) - elf_hwcap |= HWCAP_S390_ETF3EH; - - /* - * Check for additional facilities with store-facility-list-extended. - * stfle stores doublewords (8 byte) with bit 1ULL<<63 as bit 0 - * and 1ULL<<0 as bit 63. Bits 0-31 contain the same information - * as stored by stfl, bits 32-xxx contain additional facilities. - * How many facility words are stored depends on the number of - * doublewords passed to the instruction. The additional facilities - * are: - * Bit 42: decimal floating point facility is installed - * Bit 44: perform floating point operation facility is installed - * translated to: - * HWCAP_S390_DFP bit 6 (42 && 44). - */ - if ((elf_hwcap & (1UL << 2)) && test_facility(42) && test_facility(44)) - elf_hwcap |= HWCAP_S390_DFP; - - /* - * Huge page support HWCAP_S390_HPAGE is bit 7. - */ - if (MACHINE_HAS_HPAGE) - elf_hwcap |= HWCAP_S390_HPAGE; - - /* - * 64-bit register support for 31-bit processes - * HWCAP_S390_HIGH_GPRS is bit 9. - */ - elf_hwcap |= HWCAP_S390_HIGH_GPRS; - - get_cpu_id(&cpu_id); - switch (cpu_id.machine) { - case 0x9672: -#if !defined(CONFIG_64BIT) - default: /* Use "g5" as default for 31 bit kernels. */ -#endif - strcpy(elf_platform, "g5"); - break; - case 0x2064: - case 0x2066: -#if defined(CONFIG_64BIT) - default: /* Use "z900" as default for 64 bit kernels. */ -#endif - strcpy(elf_platform, "z900"); - break; - case 0x2084: - case 0x2086: - strcpy(elf_platform, "z990"); - break; - case 0x2094: - case 0x2096: - strcpy(elf_platform, "z9-109"); - break; - case 0x2097: - case 0x2098: - strcpy(elf_platform, "z10"); - break; - case 0x2817: - case 0x2818: - strcpy(elf_platform, "z196"); - break; - } -} - -/* - * Setup function called from init/main.c just after the banner - * was printed. - */ - -void __init setup_arch(char **cmdline_p) -{ - /* - * print what head.S has found out about the machine - */ -#ifndef CONFIG_64BIT - if (MACHINE_IS_VM) - pr_info("Linux is running as a z/VM " - "guest operating system in 31-bit mode\n"); - else if (MACHINE_IS_LPAR) - pr_info("Linux is running natively in 31-bit mode\n"); - if (MACHINE_HAS_IEEE) - pr_info("The hardware system has IEEE compatible " - "floating point units\n"); - else - pr_info("The hardware system has no IEEE compatible " - "floating point units\n"); -#else /* CONFIG_64BIT */ - if (MACHINE_IS_VM) - pr_info("Linux is running as a z/VM " - "guest operating system in 64-bit mode\n"); - else if (MACHINE_IS_KVM) - pr_info("Linux is running under KVM in 64-bit mode\n"); - else if (MACHINE_IS_LPAR) - pr_info("Linux is running natively in 64-bit mode\n"); -#endif /* CONFIG_64BIT */ - - /* Have one command line that is parsed and saved in /proc/cmdline */ - /* boot_command_line has been already set up in early.c */ - *cmdline_p = boot_command_line; - - ROOT_DEV = Root_RAM0; - - init_mm.start_code = PAGE_OFFSET; - init_mm.end_code = (unsigned long) &_etext; - init_mm.end_data = (unsigned long) &_edata; - init_mm.brk = (unsigned long) &_end; - - if (MACHINE_HAS_MVCOS) - memcpy(&uaccess, &uaccess_mvcos, sizeof(uaccess)); - else - memcpy(&uaccess, &uaccess_std, sizeof(uaccess)); - - parse_early_param(); - - os_info_init(); - setup_ipl(); - setup_memory_end(); - setup_addressing_mode(); - reserve_oldmem(); - reserve_crashkernel(); - setup_memory(); - setup_resources(); - setup_vmcoreinfo(); - setup_lowcore(); - - cpu_init(); - s390_init_cpu_topology(); - - /* - * Setup capabilities (ELF_HWCAP & ELF_PLATFORM). - */ - setup_hwcaps(); - - /* - * Create kernel page tables and switch to virtual addressing. - */ - paging_init(); - - /* Setup default console */ - conmode_default(); - set_preferred_console(); - - /* Setup zfcpdump support */ - setup_zfcpdump(console_devno); -} diff --git a/ANDROID_3.4.5/arch/s390/kernel/signal.c b/ANDROID_3.4.5/arch/s390/kernel/signal.c deleted file mode 100644 index f7582b27..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/signal.c +++ /dev/null @@ -1,522 +0,0 @@ -/* - * arch/s390/kernel/signal.c - * - * Copyright (C) IBM Corp. 1999,2006 - * Author(s): Denis Joseph Barrow (djbarrow@de.ibm.com,barrow_dj@yahoo.com) - * - * Based on Intel version - * - * Copyright (C) 1991, 1992 Linus Torvalds - * - * 1997-11-28 Modified for POSIX.1b signals by Richard Henderson - */ - -#include <linux/sched.h> -#include <linux/mm.h> -#include <linux/smp.h> -#include <linux/kernel.h> -#include <linux/signal.h> -#include <linux/errno.h> -#include <linux/wait.h> -#include <linux/ptrace.h> -#include <linux/unistd.h> -#include <linux/stddef.h> -#include <linux/tty.h> -#include <linux/personality.h> -#include <linux/binfmts.h> -#include <linux/tracehook.h> -#include <linux/syscalls.h> -#include <linux/compat.h> -#include <asm/ucontext.h> -#include <asm/uaccess.h> -#include <asm/lowcore.h> -#include <asm/switch_to.h> -#include "entry.h" - -#define _BLOCKABLE (~(sigmask(SIGKILL) | sigmask(SIGSTOP))) - - -typedef struct -{ - __u8 callee_used_stack[__SIGNAL_FRAMESIZE]; - struct sigcontext sc; - _sigregs sregs; - int signo; - __u8 retcode[S390_SYSCALL_SIZE]; -} sigframe; - -typedef struct -{ - __u8 callee_used_stack[__SIGNAL_FRAMESIZE]; - __u8 retcode[S390_SYSCALL_SIZE]; - struct siginfo info; - struct ucontext uc; -} rt_sigframe; - -/* - * Atomically swap in the new signal mask, and wait for a signal. - */ -SYSCALL_DEFINE3(sigsuspend, int, history0, int, history1, old_sigset_t, mask) -{ - sigset_t blocked; - - current->saved_sigmask = current->blocked; - mask &= _BLOCKABLE; - siginitset(&blocked, mask); - set_current_blocked(&blocked); - set_current_state(TASK_INTERRUPTIBLE); - schedule(); - set_restore_sigmask(); - return -ERESTARTNOHAND; -} - -SYSCALL_DEFINE3(sigaction, int, sig, const struct old_sigaction __user *, act, - struct old_sigaction __user *, oact) -{ - struct k_sigaction new_ka, old_ka; - int ret; - - if (act) { - old_sigset_t mask; - if (!access_ok(VERIFY_READ, act, sizeof(*act)) || - __get_user(new_ka.sa.sa_handler, &act->sa_handler) || - __get_user(new_ka.sa.sa_restorer, &act->sa_restorer) || - __get_user(new_ka.sa.sa_flags, &act->sa_flags) || - __get_user(mask, &act->sa_mask)) - return -EFAULT; - siginitset(&new_ka.sa.sa_mask, mask); - } - - ret = do_sigaction(sig, act ? &new_ka : NULL, oact ? &old_ka : NULL); - - if (!ret && oact) { - if (!access_ok(VERIFY_WRITE, oact, sizeof(*oact)) || - __put_user(old_ka.sa.sa_handler, &oact->sa_handler) || - __put_user(old_ka.sa.sa_restorer, &oact->sa_restorer) || - __put_user(old_ka.sa.sa_flags, &oact->sa_flags) || - __put_user(old_ka.sa.sa_mask.sig[0], &oact->sa_mask)) - return -EFAULT; - } - - return ret; -} - -SYSCALL_DEFINE2(sigaltstack, const stack_t __user *, uss, - stack_t __user *, uoss) -{ - struct pt_regs *regs = task_pt_regs(current); - return do_sigaltstack(uss, uoss, regs->gprs[15]); -} - -/* Returns non-zero on fault. */ -static int save_sigregs(struct pt_regs *regs, _sigregs __user *sregs) -{ - _sigregs user_sregs; - - save_access_regs(current->thread.acrs); - - /* Copy a 'clean' PSW mask to the user to avoid leaking - information about whether PER is currently on. */ - user_sregs.regs.psw.mask = psw_user_bits | - (regs->psw.mask & PSW_MASK_USER); - user_sregs.regs.psw.addr = regs->psw.addr; - memcpy(&user_sregs.regs.gprs, ®s->gprs, sizeof(sregs->regs.gprs)); - memcpy(&user_sregs.regs.acrs, current->thread.acrs, - sizeof(sregs->regs.acrs)); - /* - * We have to store the fp registers to current->thread.fp_regs - * to merge them with the emulated registers. - */ - save_fp_regs(¤t->thread.fp_regs); - memcpy(&user_sregs.fpregs, ¤t->thread.fp_regs, - sizeof(s390_fp_regs)); - return __copy_to_user(sregs, &user_sregs, sizeof(_sigregs)); -} - -/* Returns positive number on error */ -static int restore_sigregs(struct pt_regs *regs, _sigregs __user *sregs) -{ - int err; - _sigregs user_sregs; - - /* Alwys make any pending restarted system call return -EINTR */ - current_thread_info()->restart_block.fn = do_no_restart_syscall; - - err = __copy_from_user(&user_sregs, sregs, sizeof(_sigregs)); - if (err) - return err; - /* Use regs->psw.mask instead of psw_user_bits to preserve PER bit. */ - regs->psw.mask = (regs->psw.mask & ~PSW_MASK_USER) | - (user_sregs.regs.psw.mask & PSW_MASK_USER); - /* Check for invalid amode */ - if (regs->psw.mask & PSW_MASK_EA) - regs->psw.mask |= PSW_MASK_BA; - regs->psw.addr = user_sregs.regs.psw.addr; - memcpy(®s->gprs, &user_sregs.regs.gprs, sizeof(sregs->regs.gprs)); - memcpy(¤t->thread.acrs, &user_sregs.regs.acrs, - sizeof(sregs->regs.acrs)); - restore_access_regs(current->thread.acrs); - - memcpy(¤t->thread.fp_regs, &user_sregs.fpregs, - sizeof(s390_fp_regs)); - current->thread.fp_regs.fpc &= FPC_VALID_MASK; - - restore_fp_regs(¤t->thread.fp_regs); - clear_thread_flag(TIF_SYSCALL); /* No longer in a system call */ - return 0; -} - -SYSCALL_DEFINE0(sigreturn) -{ - struct pt_regs *regs = task_pt_regs(current); - sigframe __user *frame = (sigframe __user *)regs->gprs[15]; - sigset_t set; - - if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) - goto badframe; - if (__copy_from_user(&set.sig, &frame->sc.oldmask, _SIGMASK_COPY_SIZE)) - goto badframe; - sigdelsetmask(&set, ~_BLOCKABLE); - set_current_blocked(&set); - if (restore_sigregs(regs, &frame->sregs)) - goto badframe; - return regs->gprs[2]; -badframe: - force_sig(SIGSEGV, current); - return 0; -} - -SYSCALL_DEFINE0(rt_sigreturn) -{ - struct pt_regs *regs = task_pt_regs(current); - rt_sigframe __user *frame = (rt_sigframe __user *)regs->gprs[15]; - sigset_t set; - - if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) - goto badframe; - if (__copy_from_user(&set.sig, &frame->uc.uc_sigmask, sizeof(set))) - goto badframe; - sigdelsetmask(&set, ~_BLOCKABLE); - set_current_blocked(&set); - if (restore_sigregs(regs, &frame->uc.uc_mcontext)) - goto badframe; - if (do_sigaltstack(&frame->uc.uc_stack, NULL, - regs->gprs[15]) == -EFAULT) - goto badframe; - return regs->gprs[2]; -badframe: - force_sig(SIGSEGV, current); - return 0; -} - -/* - * Set up a signal frame. - */ - - -/* - * Determine which stack to use.. - */ -static inline void __user * -get_sigframe(struct k_sigaction *ka, struct pt_regs * regs, size_t frame_size) -{ - unsigned long sp; - - /* Default to using normal stack */ - sp = regs->gprs[15]; - - /* Overflow on alternate signal stack gives SIGSEGV. */ - if (on_sig_stack(sp) && !on_sig_stack((sp - frame_size) & -8UL)) - return (void __user *) -1UL; - - /* This is the X/Open sanctioned signal stack switching. */ - if (ka->sa.sa_flags & SA_ONSTACK) { - if (! sas_ss_flags(sp)) - sp = current->sas_ss_sp + current->sas_ss_size; - } - - /* This is the legacy signal stack switching. */ - else if (!user_mode(regs) && - !(ka->sa.sa_flags & SA_RESTORER) && - ka->sa.sa_restorer) { - sp = (unsigned long) ka->sa.sa_restorer; - } - - return (void __user *)((sp - frame_size) & -8ul); -} - -static inline int map_signal(int sig) -{ - if (current_thread_info()->exec_domain - && current_thread_info()->exec_domain->signal_invmap - && sig < 32) - return current_thread_info()->exec_domain->signal_invmap[sig]; - else - return sig; -} - -static int setup_frame(int sig, struct k_sigaction *ka, - sigset_t *set, struct pt_regs * regs) -{ - sigframe __user *frame; - - frame = get_sigframe(ka, regs, sizeof(sigframe)); - if (!access_ok(VERIFY_WRITE, frame, sizeof(sigframe))) - goto give_sigsegv; - - if (frame == (void __user *) -1UL) - goto give_sigsegv; - - if (__copy_to_user(&frame->sc.oldmask, &set->sig, _SIGMASK_COPY_SIZE)) - goto give_sigsegv; - - if (save_sigregs(regs, &frame->sregs)) - goto give_sigsegv; - if (__put_user(&frame->sregs, &frame->sc.sregs)) - goto give_sigsegv; - - /* Set up to return from userspace. If provided, use a stub - already in userspace. */ - if (ka->sa.sa_flags & SA_RESTORER) { - regs->gprs[14] = (unsigned long) - ka->sa.sa_restorer | PSW_ADDR_AMODE; - } else { - regs->gprs[14] = (unsigned long) - frame->retcode | PSW_ADDR_AMODE; - if (__put_user(S390_SYSCALL_OPCODE | __NR_sigreturn, - (u16 __user *)(frame->retcode))) - goto give_sigsegv; - } - - /* Set up backchain. */ - if (__put_user(regs->gprs[15], (addr_t __user *) frame)) - goto give_sigsegv; - - /* Set up registers for signal handler */ - regs->gprs[15] = (unsigned long) frame; - regs->psw.mask |= PSW_MASK_EA | PSW_MASK_BA; /* 64 bit amode */ - regs->psw.addr = (unsigned long) ka->sa.sa_handler | PSW_ADDR_AMODE; - - regs->gprs[2] = map_signal(sig); - regs->gprs[3] = (unsigned long) &frame->sc; - - /* We forgot to include these in the sigcontext. - To avoid breaking binary compatibility, they are passed as args. */ - if (sig == SIGSEGV || sig == SIGBUS || sig == SIGILL || - sig == SIGTRAP || sig == SIGFPE) { - /* set extra registers only for synchronous signals */ - regs->gprs[4] = regs->int_code & 127; - regs->gprs[5] = regs->int_parm_long; - regs->gprs[6] = task_thread_info(current)->last_break; - } - - /* Place signal number on stack to allow backtrace from handler. */ - if (__put_user(regs->gprs[2], (int __user *) &frame->signo)) - goto give_sigsegv; - return 0; - -give_sigsegv: - force_sigsegv(sig, current); - return -EFAULT; -} - -static int setup_rt_frame(int sig, struct k_sigaction *ka, siginfo_t *info, - sigset_t *set, struct pt_regs * regs) -{ - int err = 0; - rt_sigframe __user *frame; - - frame = get_sigframe(ka, regs, sizeof(rt_sigframe)); - if (!access_ok(VERIFY_WRITE, frame, sizeof(rt_sigframe))) - goto give_sigsegv; - - if (frame == (void __user *) -1UL) - goto give_sigsegv; - - if (copy_siginfo_to_user(&frame->info, info)) - goto give_sigsegv; - - /* Create the ucontext. */ - err |= __put_user(0, &frame->uc.uc_flags); - err |= __put_user(NULL, &frame->uc.uc_link); - err |= __put_user((void __user *)current->sas_ss_sp, &frame->uc.uc_stack.ss_sp); - err |= __put_user(sas_ss_flags(regs->gprs[15]), - &frame->uc.uc_stack.ss_flags); - err |= __put_user(current->sas_ss_size, &frame->uc.uc_stack.ss_size); - err |= save_sigregs(regs, &frame->uc.uc_mcontext); - err |= __copy_to_user(&frame->uc.uc_sigmask, set, sizeof(*set)); - if (err) - goto give_sigsegv; - - /* Set up to return from userspace. If provided, use a stub - already in userspace. */ - if (ka->sa.sa_flags & SA_RESTORER) { - regs->gprs[14] = (unsigned long) - ka->sa.sa_restorer | PSW_ADDR_AMODE; - } else { - regs->gprs[14] = (unsigned long) - frame->retcode | PSW_ADDR_AMODE; - if (__put_user(S390_SYSCALL_OPCODE | __NR_rt_sigreturn, - (u16 __user *)(frame->retcode))) - goto give_sigsegv; - } - - /* Set up backchain. */ - if (__put_user(regs->gprs[15], (addr_t __user *) frame)) - goto give_sigsegv; - - /* Set up registers for signal handler */ - regs->gprs[15] = (unsigned long) frame; - regs->psw.mask |= PSW_MASK_EA | PSW_MASK_BA; /* 64 bit amode */ - regs->psw.addr = (unsigned long) ka->sa.sa_handler | PSW_ADDR_AMODE; - - regs->gprs[2] = map_signal(sig); - regs->gprs[3] = (unsigned long) &frame->info; - regs->gprs[4] = (unsigned long) &frame->uc; - regs->gprs[5] = task_thread_info(current)->last_break; - return 0; - -give_sigsegv: - force_sigsegv(sig, current); - return -EFAULT; -} - -static int handle_signal(unsigned long sig, struct k_sigaction *ka, - siginfo_t *info, sigset_t *oldset, - struct pt_regs *regs) -{ - int ret; - - /* Set up the stack frame */ - if (ka->sa.sa_flags & SA_SIGINFO) - ret = setup_rt_frame(sig, ka, info, oldset, regs); - else - ret = setup_frame(sig, ka, oldset, regs); - if (ret) - return ret; - block_sigmask(ka, sig); - return 0; -} - -/* - * Note that 'init' is a special process: it doesn't get signals it doesn't - * want to handle. Thus you cannot kill init even with a SIGKILL even by - * mistake. - * - * Note that we go through the signals twice: once to check the signals that - * the kernel can handle, and then we build all the user-level signal handling - * stack-frames in one go after that. - */ -void do_signal(struct pt_regs *regs) -{ - siginfo_t info; - int signr; - struct k_sigaction ka; - sigset_t *oldset; - - /* - * We want the common case to go fast, which - * is why we may in certain cases get here from - * kernel mode. Just return without doing anything - * if so. - */ - if (!user_mode(regs)) - return; - - if (test_thread_flag(TIF_RESTORE_SIGMASK)) - oldset = ¤t->saved_sigmask; - else - oldset = ¤t->blocked; - - /* - * Get signal to deliver. When running under ptrace, at this point - * the debugger may change all our registers, including the system - * call information. - */ - current_thread_info()->system_call = - test_thread_flag(TIF_SYSCALL) ? regs->int_code : 0; - signr = get_signal_to_deliver(&info, &ka, regs, NULL); - - if (signr > 0) { - /* Whee! Actually deliver the signal. */ - if (current_thread_info()->system_call) { - regs->int_code = current_thread_info()->system_call; - /* Check for system call restarting. */ - switch (regs->gprs[2]) { - case -ERESTART_RESTARTBLOCK: - case -ERESTARTNOHAND: - regs->gprs[2] = -EINTR; - break; - case -ERESTARTSYS: - if (!(ka.sa.sa_flags & SA_RESTART)) { - regs->gprs[2] = -EINTR; - break; - } - /* fallthrough */ - case -ERESTARTNOINTR: - regs->gprs[2] = regs->orig_gpr2; - regs->psw.addr = - __rewind_psw(regs->psw, - regs->int_code >> 16); - break; - } - } - /* No longer in a system call */ - clear_thread_flag(TIF_SYSCALL); - - if ((is_compat_task() ? - handle_signal32(signr, &ka, &info, oldset, regs) : - handle_signal(signr, &ka, &info, oldset, regs)) == 0) { - /* - * A signal was successfully delivered; the saved - * sigmask will have been stored in the signal frame, - * and will be restored by sigreturn, so we can simply - * clear the TIF_RESTORE_SIGMASK flag. - */ - if (test_thread_flag(TIF_RESTORE_SIGMASK)) - clear_thread_flag(TIF_RESTORE_SIGMASK); - - /* - * Let tracing know that we've done the handler setup. - */ - tracehook_signal_handler(signr, &info, &ka, regs, - test_thread_flag(TIF_SINGLE_STEP)); - } - return; - } - - /* No handlers present - check for system call restart */ - clear_thread_flag(TIF_SYSCALL); - if (current_thread_info()->system_call) { - regs->int_code = current_thread_info()->system_call; - switch (regs->gprs[2]) { - case -ERESTART_RESTARTBLOCK: - /* Restart with sys_restart_syscall */ - regs->int_code = __NR_restart_syscall; - /* fallthrough */ - case -ERESTARTNOHAND: - case -ERESTARTSYS: - case -ERESTARTNOINTR: - /* Restart system call with magic TIF bit. */ - regs->gprs[2] = regs->orig_gpr2; - set_thread_flag(TIF_SYSCALL); - break; - } - } - - /* - * If there's no signal to deliver, we just put the saved sigmask back. - */ - if (test_thread_flag(TIF_RESTORE_SIGMASK)) { - clear_thread_flag(TIF_RESTORE_SIGMASK); - sigprocmask(SIG_SETMASK, ¤t->saved_sigmask, NULL); - } -} - -void do_notify_resume(struct pt_regs *regs) -{ - clear_thread_flag(TIF_NOTIFY_RESUME); - tracehook_notify_resume(regs); - if (current->replacement_session_keyring) - key_replace_session_keyring(); -} diff --git a/ANDROID_3.4.5/arch/s390/kernel/smp.c b/ANDROID_3.4.5/arch/s390/kernel/smp.c deleted file mode 100644 index 1f772276..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/smp.c +++ /dev/null @@ -1,1146 +0,0 @@ -/* - * SMP related functions - * - * Copyright IBM Corp. 1999,2012 - * Author(s): Denis Joseph Barrow, - * Martin Schwidefsky <schwidefsky@de.ibm.com>, - * Heiko Carstens <heiko.carstens@de.ibm.com>, - * - * based on other smp stuff by - * (c) 1995 Alan Cox, CymruNET Ltd <alan@cymru.net> - * (c) 1998 Ingo Molnar - * - * The code outside of smp.c uses logical cpu numbers, only smp.c does - * the translation of logical to physical cpu ids. All new code that - * operates on physical cpu numbers needs to go into smp.c. - */ - -#define KMSG_COMPONENT "cpu" -#define pr_fmt(fmt) KMSG_COMPONENT ": " fmt - -#include <linux/workqueue.h> -#include <linux/module.h> -#include <linux/init.h> -#include <linux/mm.h> -#include <linux/err.h> -#include <linux/spinlock.h> -#include <linux/kernel_stat.h> -#include <linux/delay.h> -#include <linux/interrupt.h> -#include <linux/irqflags.h> -#include <linux/cpu.h> -#include <linux/slab.h> -#include <linux/crash_dump.h> -#include <asm/asm-offsets.h> -#include <asm/switch_to.h> -#include <asm/facility.h> -#include <asm/ipl.h> -#include <asm/setup.h> -#include <asm/irq.h> -#include <asm/tlbflush.h> -#include <asm/timer.h> -#include <asm/lowcore.h> -#include <asm/sclp.h> -#include <asm/vdso.h> -#include <asm/debug.h> -#include <asm/os_info.h> -#include "entry.h" - -enum { - sigp_sense = 1, - sigp_external_call = 2, - sigp_emergency_signal = 3, - sigp_start = 4, - sigp_stop = 5, - sigp_restart = 6, - sigp_stop_and_store_status = 9, - sigp_initial_cpu_reset = 11, - sigp_cpu_reset = 12, - sigp_set_prefix = 13, - sigp_store_status_at_address = 14, - sigp_store_extended_status_at_address = 15, - sigp_set_architecture = 18, - sigp_conditional_emergency_signal = 19, - sigp_sense_running = 21, -}; - -enum { - sigp_order_code_accepted = 0, - sigp_status_stored = 1, - sigp_busy = 2, - sigp_not_operational = 3, -}; - -enum { - ec_schedule = 0, - ec_call_function, - ec_call_function_single, - ec_stop_cpu, -}; - -enum { - CPU_STATE_STANDBY, - CPU_STATE_CONFIGURED, -}; - -struct pcpu { - struct cpu cpu; - struct task_struct *idle; /* idle process for the cpu */ - struct _lowcore *lowcore; /* lowcore page(s) for the cpu */ - unsigned long async_stack; /* async stack for the cpu */ - unsigned long panic_stack; /* panic stack for the cpu */ - unsigned long ec_mask; /* bit mask for ec_xxx functions */ - int state; /* physical cpu state */ - u32 status; /* last status received via sigp */ - u16 address; /* physical cpu address */ -}; - -static u8 boot_cpu_type; -static u16 boot_cpu_address; -static struct pcpu pcpu_devices[NR_CPUS]; - -DEFINE_MUTEX(smp_cpu_state_mutex); - -/* - * Signal processor helper functions. - */ -static inline int __pcpu_sigp(u16 addr, u8 order, u32 parm, u32 *status) -{ - register unsigned int reg1 asm ("1") = parm; - int cc; - - asm volatile( - " sigp %1,%2,0(%3)\n" - " ipm %0\n" - " srl %0,28\n" - : "=d" (cc), "+d" (reg1) : "d" (addr), "a" (order) : "cc"); - if (status && cc == 1) - *status = reg1; - return cc; -} - -static inline int __pcpu_sigp_relax(u16 addr, u8 order, u32 parm, u32 *status) -{ - int cc; - - while (1) { - cc = __pcpu_sigp(addr, order, parm, status); - if (cc != sigp_busy) - return cc; - cpu_relax(); - } -} - -static int pcpu_sigp_retry(struct pcpu *pcpu, u8 order, u32 parm) -{ - int cc, retry; - - for (retry = 0; ; retry++) { - cc = __pcpu_sigp(pcpu->address, order, parm, &pcpu->status); - if (cc != sigp_busy) - break; - if (retry >= 3) - udelay(10); - } - return cc; -} - -static inline int pcpu_stopped(struct pcpu *pcpu) -{ - if (__pcpu_sigp(pcpu->address, sigp_sense, - 0, &pcpu->status) != sigp_status_stored) - return 0; - /* Check for stopped and check stop state */ - return !!(pcpu->status & 0x50); -} - -static inline int pcpu_running(struct pcpu *pcpu) -{ - if (__pcpu_sigp(pcpu->address, sigp_sense_running, - 0, &pcpu->status) != sigp_status_stored) - return 1; - /* Check for running status */ - return !(pcpu->status & 0x400); -} - -/* - * Find struct pcpu by cpu address. - */ -static struct pcpu *pcpu_find_address(const struct cpumask *mask, int address) -{ - int cpu; - - for_each_cpu(cpu, mask) - if (pcpu_devices[cpu].address == address) - return pcpu_devices + cpu; - return NULL; -} - -static void pcpu_ec_call(struct pcpu *pcpu, int ec_bit) -{ - int order; - - set_bit(ec_bit, &pcpu->ec_mask); - order = pcpu_running(pcpu) ? - sigp_external_call : sigp_emergency_signal; - pcpu_sigp_retry(pcpu, order, 0); -} - -static int __cpuinit pcpu_alloc_lowcore(struct pcpu *pcpu, int cpu) -{ - struct _lowcore *lc; - - if (pcpu != &pcpu_devices[0]) { - pcpu->lowcore = (struct _lowcore *) - __get_free_pages(GFP_KERNEL | GFP_DMA, LC_ORDER); - pcpu->async_stack = __get_free_pages(GFP_KERNEL, ASYNC_ORDER); - pcpu->panic_stack = __get_free_page(GFP_KERNEL); - if (!pcpu->lowcore || !pcpu->panic_stack || !pcpu->async_stack) - goto out; - } - lc = pcpu->lowcore; - memcpy(lc, &S390_lowcore, 512); - memset((char *) lc + 512, 0, sizeof(*lc) - 512); - lc->async_stack = pcpu->async_stack + ASYNC_SIZE; - lc->panic_stack = pcpu->panic_stack + PAGE_SIZE; - lc->cpu_nr = cpu; -#ifndef CONFIG_64BIT - if (MACHINE_HAS_IEEE) { - lc->extended_save_area_addr = get_zeroed_page(GFP_KERNEL); - if (!lc->extended_save_area_addr) - goto out; - } -#else - if (vdso_alloc_per_cpu(lc)) - goto out; -#endif - lowcore_ptr[cpu] = lc; - pcpu_sigp_retry(pcpu, sigp_set_prefix, (u32)(unsigned long) lc); - return 0; -out: - if (pcpu != &pcpu_devices[0]) { - free_page(pcpu->panic_stack); - free_pages(pcpu->async_stack, ASYNC_ORDER); - free_pages((unsigned long) pcpu->lowcore, LC_ORDER); - } - return -ENOMEM; -} - -static void pcpu_free_lowcore(struct pcpu *pcpu) -{ - pcpu_sigp_retry(pcpu, sigp_set_prefix, 0); - lowcore_ptr[pcpu - pcpu_devices] = NULL; -#ifndef CONFIG_64BIT - if (MACHINE_HAS_IEEE) { - struct _lowcore *lc = pcpu->lowcore; - - free_page((unsigned long) lc->extended_save_area_addr); - lc->extended_save_area_addr = 0; - } -#else - vdso_free_per_cpu(pcpu->lowcore); -#endif - if (pcpu != &pcpu_devices[0]) { - free_page(pcpu->panic_stack); - free_pages(pcpu->async_stack, ASYNC_ORDER); - free_pages((unsigned long) pcpu->lowcore, LC_ORDER); - } -} - -static void pcpu_prepare_secondary(struct pcpu *pcpu, int cpu) -{ - struct _lowcore *lc = pcpu->lowcore; - - atomic_inc(&init_mm.context.attach_count); - lc->cpu_nr = cpu; - lc->percpu_offset = __per_cpu_offset[cpu]; - lc->kernel_asce = S390_lowcore.kernel_asce; - lc->machine_flags = S390_lowcore.machine_flags; - lc->ftrace_func = S390_lowcore.ftrace_func; - lc->user_timer = lc->system_timer = lc->steal_timer = 0; - __ctl_store(lc->cregs_save_area, 0, 15); - save_access_regs((unsigned int *) lc->access_regs_save_area); - memcpy(lc->stfle_fac_list, S390_lowcore.stfle_fac_list, - MAX_FACILITY_BIT/8); -} - -static void pcpu_attach_task(struct pcpu *pcpu, struct task_struct *tsk) -{ - struct _lowcore *lc = pcpu->lowcore; - struct thread_info *ti = task_thread_info(tsk); - - lc->kernel_stack = (unsigned long) task_stack_page(tsk) + THREAD_SIZE; - lc->thread_info = (unsigned long) task_thread_info(tsk); - lc->current_task = (unsigned long) tsk; - lc->user_timer = ti->user_timer; - lc->system_timer = ti->system_timer; - lc->steal_timer = 0; -} - -static void pcpu_start_fn(struct pcpu *pcpu, void (*func)(void *), void *data) -{ - struct _lowcore *lc = pcpu->lowcore; - - lc->restart_stack = lc->kernel_stack; - lc->restart_fn = (unsigned long) func; - lc->restart_data = (unsigned long) data; - lc->restart_source = -1UL; - pcpu_sigp_retry(pcpu, sigp_restart, 0); -} - -/* - * Call function via PSW restart on pcpu and stop the current cpu. - */ -static void pcpu_delegate(struct pcpu *pcpu, void (*func)(void *), - void *data, unsigned long stack) -{ - struct _lowcore *lc = pcpu->lowcore; - unsigned short this_cpu; - - __load_psw_mask(psw_kernel_bits); - this_cpu = stap(); - if (pcpu->address == this_cpu) - func(data); /* should not return */ - /* Stop target cpu (if func returns this stops the current cpu). */ - pcpu_sigp_retry(pcpu, sigp_stop, 0); - /* Restart func on the target cpu and stop the current cpu. */ - lc->restart_stack = stack; - lc->restart_fn = (unsigned long) func; - lc->restart_data = (unsigned long) data; - lc->restart_source = (unsigned long) this_cpu; - asm volatile( - "0: sigp 0,%0,6 # sigp restart to target cpu\n" - " brc 2,0b # busy, try again\n" - "1: sigp 0,%1,5 # sigp stop to current cpu\n" - " brc 2,1b # busy, try again\n" - : : "d" (pcpu->address), "d" (this_cpu) : "0", "1", "cc"); - for (;;) ; -} - -/* - * Call function on an online CPU. - */ -void smp_call_online_cpu(void (*func)(void *), void *data) -{ - struct pcpu *pcpu; - - /* Use the current cpu if it is online. */ - pcpu = pcpu_find_address(cpu_online_mask, stap()); - if (!pcpu) - /* Use the first online cpu. */ - pcpu = pcpu_devices + cpumask_first(cpu_online_mask); - pcpu_delegate(pcpu, func, data, (unsigned long) restart_stack); -} - -/* - * Call function on the ipl CPU. - */ -void smp_call_ipl_cpu(void (*func)(void *), void *data) -{ - pcpu_delegate(&pcpu_devices[0], func, data, - pcpu_devices->panic_stack + PAGE_SIZE); -} - -int smp_find_processor_id(u16 address) -{ - int cpu; - - for_each_present_cpu(cpu) - if (pcpu_devices[cpu].address == address) - return cpu; - return -1; -} - -int smp_vcpu_scheduled(int cpu) -{ - return pcpu_running(pcpu_devices + cpu); -} - -void smp_yield(void) -{ - if (MACHINE_HAS_DIAG44) - asm volatile("diag 0,0,0x44"); -} - -void smp_yield_cpu(int cpu) -{ - if (MACHINE_HAS_DIAG9C) - asm volatile("diag %0,0,0x9c" - : : "d" (pcpu_devices[cpu].address)); - else if (MACHINE_HAS_DIAG44) - asm volatile("diag 0,0,0x44"); -} - -/* - * Send cpus emergency shutdown signal. This gives the cpus the - * opportunity to complete outstanding interrupts. - */ -void smp_emergency_stop(cpumask_t *cpumask) -{ - u64 end; - int cpu; - - end = get_clock() + (1000000UL << 12); - for_each_cpu(cpu, cpumask) { - struct pcpu *pcpu = pcpu_devices + cpu; - set_bit(ec_stop_cpu, &pcpu->ec_mask); - while (__pcpu_sigp(pcpu->address, sigp_emergency_signal, - 0, NULL) == sigp_busy && - get_clock() < end) - cpu_relax(); - } - while (get_clock() < end) { - for_each_cpu(cpu, cpumask) - if (pcpu_stopped(pcpu_devices + cpu)) - cpumask_clear_cpu(cpu, cpumask); - if (cpumask_empty(cpumask)) - break; - cpu_relax(); - } -} - -/* - * Stop all cpus but the current one. - */ -void smp_send_stop(void) -{ - cpumask_t cpumask; - int cpu; - - /* Disable all interrupts/machine checks */ - __load_psw_mask(psw_kernel_bits | PSW_MASK_DAT); - trace_hardirqs_off(); - - debug_set_critical(); - cpumask_copy(&cpumask, cpu_online_mask); - cpumask_clear_cpu(smp_processor_id(), &cpumask); - - if (oops_in_progress) - smp_emergency_stop(&cpumask); - - /* stop all processors */ - for_each_cpu(cpu, &cpumask) { - struct pcpu *pcpu = pcpu_devices + cpu; - pcpu_sigp_retry(pcpu, sigp_stop, 0); - while (!pcpu_stopped(pcpu)) - cpu_relax(); - } -} - -/* - * Stop the current cpu. - */ -void smp_stop_cpu(void) -{ - pcpu_sigp_retry(pcpu_devices + smp_processor_id(), sigp_stop, 0); - for (;;) ; -} - -/* - * This is the main routine where commands issued by other - * cpus are handled. - */ -static void do_ext_call_interrupt(struct ext_code ext_code, - unsigned int param32, unsigned long param64) -{ - unsigned long bits; - int cpu; - - cpu = smp_processor_id(); - if (ext_code.code == 0x1202) - kstat_cpu(cpu).irqs[EXTINT_EXC]++; - else - kstat_cpu(cpu).irqs[EXTINT_EMS]++; - /* - * handle bit signal external calls - */ - bits = xchg(&pcpu_devices[cpu].ec_mask, 0); - - if (test_bit(ec_stop_cpu, &bits)) - smp_stop_cpu(); - - if (test_bit(ec_schedule, &bits)) - scheduler_ipi(); - - if (test_bit(ec_call_function, &bits)) - generic_smp_call_function_interrupt(); - - if (test_bit(ec_call_function_single, &bits)) - generic_smp_call_function_single_interrupt(); - -} - -void arch_send_call_function_ipi_mask(const struct cpumask *mask) -{ - int cpu; - - for_each_cpu(cpu, mask) - pcpu_ec_call(pcpu_devices + cpu, ec_call_function); -} - -void arch_send_call_function_single_ipi(int cpu) -{ - pcpu_ec_call(pcpu_devices + cpu, ec_call_function_single); -} - -#ifndef CONFIG_64BIT -/* - * this function sends a 'purge tlb' signal to another CPU. - */ -static void smp_ptlb_callback(void *info) -{ - __tlb_flush_local(); -} - -void smp_ptlb_all(void) -{ - on_each_cpu(smp_ptlb_callback, NULL, 1); -} -EXPORT_SYMBOL(smp_ptlb_all); -#endif /* ! CONFIG_64BIT */ - -/* - * this function sends a 'reschedule' IPI to another CPU. - * it goes straight through and wastes no time serializing - * anything. Worst case is that we lose a reschedule ... - */ -void smp_send_reschedule(int cpu) -{ - pcpu_ec_call(pcpu_devices + cpu, ec_schedule); -} - -/* - * parameter area for the set/clear control bit callbacks - */ -struct ec_creg_mask_parms { - unsigned long orval; - unsigned long andval; - int cr; -}; - -/* - * callback for setting/clearing control bits - */ -static void smp_ctl_bit_callback(void *info) -{ - struct ec_creg_mask_parms *pp = info; - unsigned long cregs[16]; - - __ctl_store(cregs, 0, 15); - cregs[pp->cr] = (cregs[pp->cr] & pp->andval) | pp->orval; - __ctl_load(cregs, 0, 15); -} - -/* - * Set a bit in a control register of all cpus - */ -void smp_ctl_set_bit(int cr, int bit) -{ - struct ec_creg_mask_parms parms = { 1UL << bit, -1UL, cr }; - - on_each_cpu(smp_ctl_bit_callback, &parms, 1); -} -EXPORT_SYMBOL(smp_ctl_set_bit); - -/* - * Clear a bit in a control register of all cpus - */ -void smp_ctl_clear_bit(int cr, int bit) -{ - struct ec_creg_mask_parms parms = { 0, ~(1UL << bit), cr }; - - on_each_cpu(smp_ctl_bit_callback, &parms, 1); -} -EXPORT_SYMBOL(smp_ctl_clear_bit); - -#if defined(CONFIG_ZFCPDUMP) || defined(CONFIG_CRASH_DUMP) - -struct save_area *zfcpdump_save_areas[NR_CPUS + 1]; -EXPORT_SYMBOL_GPL(zfcpdump_save_areas); - -static void __init smp_get_save_area(int cpu, u16 address) -{ - void *lc = pcpu_devices[0].lowcore; - struct save_area *save_area; - - if (is_kdump_kernel()) - return; - if (!OLDMEM_BASE && (address == boot_cpu_address || - ipl_info.type != IPL_TYPE_FCP_DUMP)) - return; - if (cpu >= NR_CPUS) { - pr_warning("CPU %i exceeds the maximum %i and is excluded " - "from the dump\n", cpu, NR_CPUS - 1); - return; - } - save_area = kmalloc(sizeof(struct save_area), GFP_KERNEL); - if (!save_area) - panic("could not allocate memory for save area\n"); - zfcpdump_save_areas[cpu] = save_area; -#ifdef CONFIG_CRASH_DUMP - if (address == boot_cpu_address) { - /* Copy the registers of the boot cpu. */ - copy_oldmem_page(1, (void *) save_area, sizeof(*save_area), - SAVE_AREA_BASE - PAGE_SIZE, 0); - return; - } -#endif - /* Get the registers of a non-boot cpu. */ - __pcpu_sigp_relax(address, sigp_stop_and_store_status, 0, NULL); - memcpy_real(save_area, lc + SAVE_AREA_BASE, sizeof(*save_area)); -} - -int smp_store_status(int cpu) -{ - struct pcpu *pcpu; - - pcpu = pcpu_devices + cpu; - if (__pcpu_sigp_relax(pcpu->address, sigp_stop_and_store_status, - 0, NULL) != sigp_order_code_accepted) - return -EIO; - return 0; -} - -#else /* CONFIG_ZFCPDUMP || CONFIG_CRASH_DUMP */ - -static inline void smp_get_save_area(int cpu, u16 address) { } - -#endif /* CONFIG_ZFCPDUMP || CONFIG_CRASH_DUMP */ - -static struct sclp_cpu_info *smp_get_cpu_info(void) -{ - static int use_sigp_detection; - struct sclp_cpu_info *info; - int address; - - info = kzalloc(sizeof(*info), GFP_KERNEL); - if (info && (use_sigp_detection || sclp_get_cpu_info(info))) { - use_sigp_detection = 1; - for (address = 0; address <= MAX_CPU_ADDRESS; address++) { - if (__pcpu_sigp_relax(address, sigp_sense, 0, NULL) == - sigp_not_operational) - continue; - info->cpu[info->configured].address = address; - info->configured++; - } - info->combined = info->configured; - } - return info; -} - -static int __devinit smp_add_present_cpu(int cpu); - -static int __devinit __smp_rescan_cpus(struct sclp_cpu_info *info, - int sysfs_add) -{ - struct pcpu *pcpu; - cpumask_t avail; - int cpu, nr, i; - - nr = 0; - cpumask_xor(&avail, cpu_possible_mask, cpu_present_mask); - cpu = cpumask_first(&avail); - for (i = 0; (i < info->combined) && (cpu < nr_cpu_ids); i++) { - if (info->has_cpu_type && info->cpu[i].type != boot_cpu_type) - continue; - if (pcpu_find_address(cpu_present_mask, info->cpu[i].address)) - continue; - pcpu = pcpu_devices + cpu; - pcpu->address = info->cpu[i].address; - pcpu->state = (cpu >= info->configured) ? - CPU_STATE_STANDBY : CPU_STATE_CONFIGURED; - cpu_set_polarization(cpu, POLARIZATION_UNKNOWN); - set_cpu_present(cpu, true); - if (sysfs_add && smp_add_present_cpu(cpu) != 0) - set_cpu_present(cpu, false); - else - nr++; - cpu = cpumask_next(cpu, &avail); - } - return nr; -} - -static void __init smp_detect_cpus(void) -{ - unsigned int cpu, c_cpus, s_cpus; - struct sclp_cpu_info *info; - - info = smp_get_cpu_info(); - if (!info) - panic("smp_detect_cpus failed to allocate memory\n"); - if (info->has_cpu_type) { - for (cpu = 0; cpu < info->combined; cpu++) { - if (info->cpu[cpu].address != boot_cpu_address) - continue; - /* The boot cpu dictates the cpu type. */ - boot_cpu_type = info->cpu[cpu].type; - break; - } - } - c_cpus = s_cpus = 0; - for (cpu = 0; cpu < info->combined; cpu++) { - if (info->has_cpu_type && info->cpu[cpu].type != boot_cpu_type) - continue; - if (cpu < info->configured) { - smp_get_save_area(c_cpus, info->cpu[cpu].address); - c_cpus++; - } else - s_cpus++; - } - pr_info("%d configured CPUs, %d standby CPUs\n", c_cpus, s_cpus); - get_online_cpus(); - __smp_rescan_cpus(info, 0); - put_online_cpus(); - kfree(info); -} - -/* - * Activate a secondary processor. - */ -static void __cpuinit smp_start_secondary(void *cpuvoid) -{ - S390_lowcore.last_update_clock = get_clock(); - S390_lowcore.restart_stack = (unsigned long) restart_stack; - S390_lowcore.restart_fn = (unsigned long) do_restart; - S390_lowcore.restart_data = 0; - S390_lowcore.restart_source = -1UL; - restore_access_regs(S390_lowcore.access_regs_save_area); - __ctl_load(S390_lowcore.cregs_save_area, 0, 15); - __load_psw_mask(psw_kernel_bits | PSW_MASK_DAT); - cpu_init(); - preempt_disable(); - init_cpu_timer(); - init_cpu_vtimer(); - pfault_init(); - notify_cpu_starting(smp_processor_id()); - ipi_call_lock(); - set_cpu_online(smp_processor_id(), true); - ipi_call_unlock(); - local_irq_enable(); - /* cpu_idle will call schedule for us */ - cpu_idle(); -} - -struct create_idle { - struct work_struct work; - struct task_struct *idle; - struct completion done; - int cpu; -}; - -static void __cpuinit smp_fork_idle(struct work_struct *work) -{ - struct create_idle *c_idle; - - c_idle = container_of(work, struct create_idle, work); - c_idle->idle = fork_idle(c_idle->cpu); - complete(&c_idle->done); -} - -/* Upping and downing of CPUs */ -int __cpuinit __cpu_up(unsigned int cpu) -{ - struct create_idle c_idle; - struct pcpu *pcpu; - int rc; - - pcpu = pcpu_devices + cpu; - if (pcpu->state != CPU_STATE_CONFIGURED) - return -EIO; - if (pcpu_sigp_retry(pcpu, sigp_initial_cpu_reset, 0) != - sigp_order_code_accepted) - return -EIO; - if (!pcpu->idle) { - c_idle.done = COMPLETION_INITIALIZER_ONSTACK(c_idle.done); - INIT_WORK_ONSTACK(&c_idle.work, smp_fork_idle); - c_idle.cpu = cpu; - schedule_work(&c_idle.work); - wait_for_completion(&c_idle.done); - if (IS_ERR(c_idle.idle)) - return PTR_ERR(c_idle.idle); - pcpu->idle = c_idle.idle; - } - init_idle(pcpu->idle, cpu); - rc = pcpu_alloc_lowcore(pcpu, cpu); - if (rc) - return rc; - pcpu_prepare_secondary(pcpu, cpu); - pcpu_attach_task(pcpu, pcpu->idle); - pcpu_start_fn(pcpu, smp_start_secondary, NULL); - while (!cpu_online(cpu)) - cpu_relax(); - return 0; -} - -static int __init setup_possible_cpus(char *s) -{ - int max, cpu; - - if (kstrtoint(s, 0, &max) < 0) - return 0; - init_cpu_possible(cpumask_of(0)); - for (cpu = 1; cpu < max && cpu < nr_cpu_ids; cpu++) - set_cpu_possible(cpu, true); - return 0; -} -early_param("possible_cpus", setup_possible_cpus); - -#ifdef CONFIG_HOTPLUG_CPU - -int __cpu_disable(void) -{ - unsigned long cregs[16]; - - set_cpu_online(smp_processor_id(), false); - /* Disable pseudo page faults on this cpu. */ - pfault_fini(); - /* Disable interrupt sources via control register. */ - __ctl_store(cregs, 0, 15); - cregs[0] &= ~0x0000ee70UL; /* disable all external interrupts */ - cregs[6] &= ~0xff000000UL; /* disable all I/O interrupts */ - cregs[14] &= ~0x1f000000UL; /* disable most machine checks */ - __ctl_load(cregs, 0, 15); - return 0; -} - -void __cpu_die(unsigned int cpu) -{ - struct pcpu *pcpu; - - /* Wait until target cpu is down */ - pcpu = pcpu_devices + cpu; - while (!pcpu_stopped(pcpu)) - cpu_relax(); - pcpu_free_lowcore(pcpu); - atomic_dec(&init_mm.context.attach_count); -} - -void __noreturn cpu_die(void) -{ - idle_task_exit(); - pcpu_sigp_retry(pcpu_devices + smp_processor_id(), sigp_stop, 0); - for (;;) ; -} - -#endif /* CONFIG_HOTPLUG_CPU */ - -static void smp_call_os_info_init_fn(void) -{ - int (*init_fn)(void); - unsigned long size; - - init_fn = os_info_old_entry(OS_INFO_INIT_FN, &size); - if (!init_fn) - return; - init_fn(); -} - -void __init smp_prepare_cpus(unsigned int max_cpus) -{ - /* request the 0x1201 emergency signal external interrupt */ - if (register_external_interrupt(0x1201, do_ext_call_interrupt) != 0) - panic("Couldn't request external interrupt 0x1201"); - /* request the 0x1202 external call external interrupt */ - if (register_external_interrupt(0x1202, do_ext_call_interrupt) != 0) - panic("Couldn't request external interrupt 0x1202"); - smp_call_os_info_init_fn(); - smp_detect_cpus(); -} - -void __init smp_prepare_boot_cpu(void) -{ - struct pcpu *pcpu = pcpu_devices; - - boot_cpu_address = stap(); - pcpu->idle = current; - pcpu->state = CPU_STATE_CONFIGURED; - pcpu->address = boot_cpu_address; - pcpu->lowcore = (struct _lowcore *)(unsigned long) store_prefix(); - pcpu->async_stack = S390_lowcore.async_stack - ASYNC_SIZE; - pcpu->panic_stack = S390_lowcore.panic_stack - PAGE_SIZE; - S390_lowcore.percpu_offset = __per_cpu_offset[0]; - cpu_set_polarization(0, POLARIZATION_UNKNOWN); - set_cpu_present(0, true); - set_cpu_online(0, true); -} - -void __init smp_cpus_done(unsigned int max_cpus) -{ -} - -void __init smp_setup_processor_id(void) -{ - S390_lowcore.cpu_nr = 0; -} - -/* - * the frequency of the profiling timer can be changed - * by writing a multiplier value into /proc/profile. - * - * usually you want to run this on all CPUs ;) - */ -int setup_profiling_timer(unsigned int multiplier) -{ - return 0; -} - -#ifdef CONFIG_HOTPLUG_CPU -static ssize_t cpu_configure_show(struct device *dev, - struct device_attribute *attr, char *buf) -{ - ssize_t count; - - mutex_lock(&smp_cpu_state_mutex); - count = sprintf(buf, "%d\n", pcpu_devices[dev->id].state); - mutex_unlock(&smp_cpu_state_mutex); - return count; -} - -static ssize_t cpu_configure_store(struct device *dev, - struct device_attribute *attr, - const char *buf, size_t count) -{ - struct pcpu *pcpu; - int cpu, val, rc; - char delim; - - if (sscanf(buf, "%d %c", &val, &delim) != 1) - return -EINVAL; - if (val != 0 && val != 1) - return -EINVAL; - get_online_cpus(); - mutex_lock(&smp_cpu_state_mutex); - rc = -EBUSY; - /* disallow configuration changes of online cpus and cpu 0 */ - cpu = dev->id; - if (cpu_online(cpu) || cpu == 0) - goto out; - pcpu = pcpu_devices + cpu; - rc = 0; - switch (val) { - case 0: - if (pcpu->state != CPU_STATE_CONFIGURED) - break; - rc = sclp_cpu_deconfigure(pcpu->address); - if (rc) - break; - pcpu->state = CPU_STATE_STANDBY; - cpu_set_polarization(cpu, POLARIZATION_UNKNOWN); - topology_expect_change(); - break; - case 1: - if (pcpu->state != CPU_STATE_STANDBY) - break; - rc = sclp_cpu_configure(pcpu->address); - if (rc) - break; - pcpu->state = CPU_STATE_CONFIGURED; - cpu_set_polarization(cpu, POLARIZATION_UNKNOWN); - topology_expect_change(); - break; - default: - break; - } -out: - mutex_unlock(&smp_cpu_state_mutex); - put_online_cpus(); - return rc ? rc : count; -} -static DEVICE_ATTR(configure, 0644, cpu_configure_show, cpu_configure_store); -#endif /* CONFIG_HOTPLUG_CPU */ - -static ssize_t show_cpu_address(struct device *dev, - struct device_attribute *attr, char *buf) -{ - return sprintf(buf, "%d\n", pcpu_devices[dev->id].address); -} -static DEVICE_ATTR(address, 0444, show_cpu_address, NULL); - -static struct attribute *cpu_common_attrs[] = { -#ifdef CONFIG_HOTPLUG_CPU - &dev_attr_configure.attr, -#endif - &dev_attr_address.attr, - NULL, -}; - -static struct attribute_group cpu_common_attr_group = { - .attrs = cpu_common_attrs, -}; - -static ssize_t show_capability(struct device *dev, - struct device_attribute *attr, char *buf) -{ - unsigned int capability; - int rc; - - rc = get_cpu_capability(&capability); - if (rc) - return rc; - return sprintf(buf, "%u\n", capability); -} -static DEVICE_ATTR(capability, 0444, show_capability, NULL); - -static ssize_t show_idle_count(struct device *dev, - struct device_attribute *attr, char *buf) -{ - struct s390_idle_data *idle = &per_cpu(s390_idle, dev->id); - unsigned long long idle_count; - unsigned int sequence; - - do { - sequence = ACCESS_ONCE(idle->sequence); - idle_count = ACCESS_ONCE(idle->idle_count); - if (ACCESS_ONCE(idle->idle_enter)) - idle_count++; - } while ((sequence & 1) || (idle->sequence != sequence)); - return sprintf(buf, "%llu\n", idle_count); -} -static DEVICE_ATTR(idle_count, 0444, show_idle_count, NULL); - -static ssize_t show_idle_time(struct device *dev, - struct device_attribute *attr, char *buf) -{ - struct s390_idle_data *idle = &per_cpu(s390_idle, dev->id); - unsigned long long now, idle_time, idle_enter, idle_exit; - unsigned int sequence; - - do { - now = get_clock(); - sequence = ACCESS_ONCE(idle->sequence); - idle_time = ACCESS_ONCE(idle->idle_time); - idle_enter = ACCESS_ONCE(idle->idle_enter); - idle_exit = ACCESS_ONCE(idle->idle_exit); - } while ((sequence & 1) || (idle->sequence != sequence)); - idle_time += idle_enter ? ((idle_exit ? : now) - idle_enter) : 0; - return sprintf(buf, "%llu\n", idle_time >> 12); -} -static DEVICE_ATTR(idle_time_us, 0444, show_idle_time, NULL); - -static struct attribute *cpu_online_attrs[] = { - &dev_attr_capability.attr, - &dev_attr_idle_count.attr, - &dev_attr_idle_time_us.attr, - NULL, -}; - -static struct attribute_group cpu_online_attr_group = { - .attrs = cpu_online_attrs, -}; - -static int __cpuinit smp_cpu_notify(struct notifier_block *self, - unsigned long action, void *hcpu) -{ - unsigned int cpu = (unsigned int)(long)hcpu; - struct cpu *c = &pcpu_devices[cpu].cpu; - struct device *s = &c->dev; - struct s390_idle_data *idle; - int err = 0; - - switch (action) { - case CPU_ONLINE: - case CPU_ONLINE_FROZEN: - idle = &per_cpu(s390_idle, cpu); - memset(idle, 0, sizeof(struct s390_idle_data)); - err = sysfs_create_group(&s->kobj, &cpu_online_attr_group); - break; - case CPU_DEAD: - case CPU_DEAD_FROZEN: - sysfs_remove_group(&s->kobj, &cpu_online_attr_group); - break; - } - return notifier_from_errno(err); -} - -static struct notifier_block __cpuinitdata smp_cpu_nb = { - .notifier_call = smp_cpu_notify, -}; - -static int __devinit smp_add_present_cpu(int cpu) -{ - struct cpu *c = &pcpu_devices[cpu].cpu; - struct device *s = &c->dev; - int rc; - - c->hotpluggable = 1; - rc = register_cpu(c, cpu); - if (rc) - goto out; - rc = sysfs_create_group(&s->kobj, &cpu_common_attr_group); - if (rc) - goto out_cpu; - if (cpu_online(cpu)) { - rc = sysfs_create_group(&s->kobj, &cpu_online_attr_group); - if (rc) - goto out_online; - } - rc = topology_cpu_init(c); - if (rc) - goto out_topology; - return 0; - -out_topology: - if (cpu_online(cpu)) - sysfs_remove_group(&s->kobj, &cpu_online_attr_group); -out_online: - sysfs_remove_group(&s->kobj, &cpu_common_attr_group); -out_cpu: -#ifdef CONFIG_HOTPLUG_CPU - unregister_cpu(c); -#endif -out: - return rc; -} - -#ifdef CONFIG_HOTPLUG_CPU - -int __ref smp_rescan_cpus(void) -{ - struct sclp_cpu_info *info; - int nr; - - info = smp_get_cpu_info(); - if (!info) - return -ENOMEM; - get_online_cpus(); - mutex_lock(&smp_cpu_state_mutex); - nr = __smp_rescan_cpus(info, 1); - mutex_unlock(&smp_cpu_state_mutex); - put_online_cpus(); - kfree(info); - if (nr) - topology_schedule_update(); - return 0; -} - -static ssize_t __ref rescan_store(struct device *dev, - struct device_attribute *attr, - const char *buf, - size_t count) -{ - int rc; - - rc = smp_rescan_cpus(); - return rc ? rc : count; -} -static DEVICE_ATTR(rescan, 0200, NULL, rescan_store); -#endif /* CONFIG_HOTPLUG_CPU */ - -static int __init s390_smp_init(void) -{ - int cpu, rc; - - register_cpu_notifier(&smp_cpu_nb); -#ifdef CONFIG_HOTPLUG_CPU - rc = device_create_file(cpu_subsys.dev_root, &dev_attr_rescan); - if (rc) - return rc; -#endif - for_each_present_cpu(cpu) { - rc = smp_add_present_cpu(cpu); - if (rc) - return rc; - } - return 0; -} -subsys_initcall(s390_smp_init); diff --git a/ANDROID_3.4.5/arch/s390/kernel/stacktrace.c b/ANDROID_3.4.5/arch/s390/kernel/stacktrace.c deleted file mode 100644 index 8841919e..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/stacktrace.c +++ /dev/null @@ -1,98 +0,0 @@ -/* - * arch/s390/kernel/stacktrace.c - * - * Stack trace management functions - * - * Copyright (C) IBM Corp. 2006 - * Author(s): Heiko Carstens <heiko.carstens@de.ibm.com> - */ - -#include <linux/sched.h> -#include <linux/stacktrace.h> -#include <linux/kallsyms.h> -#include <linux/module.h> - -static unsigned long save_context_stack(struct stack_trace *trace, - unsigned long sp, - unsigned long low, - unsigned long high, - int savesched) -{ - struct stack_frame *sf; - struct pt_regs *regs; - unsigned long addr; - - while(1) { - sp &= PSW_ADDR_INSN; - if (sp < low || sp > high) - return sp; - sf = (struct stack_frame *)sp; - while(1) { - addr = sf->gprs[8] & PSW_ADDR_INSN; - if (!trace->skip) - trace->entries[trace->nr_entries++] = addr; - else - trace->skip--; - if (trace->nr_entries >= trace->max_entries) - return sp; - low = sp; - sp = sf->back_chain & PSW_ADDR_INSN; - if (!sp) - break; - if (sp <= low || sp > high - sizeof(*sf)) - return sp; - sf = (struct stack_frame *)sp; - } - /* Zero backchain detected, check for interrupt frame. */ - sp = (unsigned long)(sf + 1); - if (sp <= low || sp > high - sizeof(*regs)) - return sp; - regs = (struct pt_regs *)sp; - addr = regs->psw.addr & PSW_ADDR_INSN; - if (savesched || !in_sched_functions(addr)) { - if (!trace->skip) - trace->entries[trace->nr_entries++] = addr; - else - trace->skip--; - } - if (trace->nr_entries >= trace->max_entries) - return sp; - low = sp; - sp = regs->gprs[15]; - } -} - -void save_stack_trace(struct stack_trace *trace) -{ - register unsigned long sp asm ("15"); - unsigned long orig_sp, new_sp; - - orig_sp = sp & PSW_ADDR_INSN; - new_sp = save_context_stack(trace, orig_sp, - S390_lowcore.panic_stack - PAGE_SIZE, - S390_lowcore.panic_stack, 1); - if (new_sp != orig_sp) - return; - new_sp = save_context_stack(trace, new_sp, - S390_lowcore.async_stack - ASYNC_SIZE, - S390_lowcore.async_stack, 1); - if (new_sp != orig_sp) - return; - save_context_stack(trace, new_sp, - S390_lowcore.thread_info, - S390_lowcore.thread_info + THREAD_SIZE, 1); -} -EXPORT_SYMBOL_GPL(save_stack_trace); - -void save_stack_trace_tsk(struct task_struct *tsk, struct stack_trace *trace) -{ - unsigned long sp, low, high; - - sp = tsk->thread.ksp & PSW_ADDR_INSN; - low = (unsigned long) task_stack_page(tsk); - high = (unsigned long) task_pt_regs(tsk); - save_context_stack(trace, sp, low, high, 0); - if (trace->nr_entries < trace->max_entries) - trace->entries[trace->nr_entries++] = ULONG_MAX; -} -EXPORT_SYMBOL_GPL(save_stack_trace_tsk); diff --git a/ANDROID_3.4.5/arch/s390/kernel/suspend.c b/ANDROID_3.4.5/arch/s390/kernel/suspend.c deleted file mode 100644 index aa1494d0..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/suspend.c +++ /dev/null @@ -1,182 +0,0 @@ -/* - * Suspend support specific for s390. - * - * Copyright IBM Corp. 2009 - * - * Author(s): Hans-Joachim Picht <hans@linux.vnet.ibm.com> - */ - -#include <linux/pfn.h> -#include <linux/suspend.h> -#include <linux/mm.h> -#include <asm/ctl_reg.h> - -/* - * References to section boundaries - */ -extern const void __nosave_begin, __nosave_end; - -/* - * The restore of the saved pages in an hibernation image will set - * the change and referenced bits in the storage key for each page. - * Overindication of the referenced bits after an hibernation cycle - * does not cause any harm but the overindication of the change bits - * would cause trouble. - * Use the ARCH_SAVE_PAGE_KEYS hooks to save the storage key of each - * page to the most significant byte of the associated page frame - * number in the hibernation image. - */ - -/* - * Key storage is allocated as a linked list of pages. - * The size of the keys array is (PAGE_SIZE - sizeof(long)) - */ -struct page_key_data { - struct page_key_data *next; - unsigned char data[]; -}; - -#define PAGE_KEY_DATA_SIZE (PAGE_SIZE - sizeof(struct page_key_data *)) - -static struct page_key_data *page_key_data; -static struct page_key_data *page_key_rp, *page_key_wp; -static unsigned long page_key_rx, page_key_wx; - -/* - * For each page in the hibernation image one additional byte is - * stored in the most significant byte of the page frame number. - * On suspend no additional memory is required but on resume the - * keys need to be memorized until the page data has been restored. - * Only then can the storage keys be set to their old state. - */ -unsigned long page_key_additional_pages(unsigned long pages) -{ - return DIV_ROUND_UP(pages, PAGE_KEY_DATA_SIZE); -} - -/* - * Free page_key_data list of arrays. - */ -void page_key_free(void) -{ - struct page_key_data *pkd; - - while (page_key_data) { - pkd = page_key_data; - page_key_data = pkd->next; - free_page((unsigned long) pkd); - } -} - -/* - * Allocate page_key_data list of arrays with enough room to store - * one byte for each page in the hibernation image. - */ -int page_key_alloc(unsigned long pages) -{ - struct page_key_data *pk; - unsigned long size; - - size = DIV_ROUND_UP(pages, PAGE_KEY_DATA_SIZE); - while (size--) { - pk = (struct page_key_data *) get_zeroed_page(GFP_KERNEL); - if (!pk) { - page_key_free(); - return -ENOMEM; - } - pk->next = page_key_data; - page_key_data = pk; - } - page_key_rp = page_key_wp = page_key_data; - page_key_rx = page_key_wx = 0; - return 0; -} - -/* - * Save the storage key into the upper 8 bits of the page frame number. - */ -void page_key_read(unsigned long *pfn) -{ - unsigned long addr; - - addr = (unsigned long) page_address(pfn_to_page(*pfn)); - *(unsigned char *) pfn = (unsigned char) page_get_storage_key(addr); -} - -/* - * Extract the storage key from the upper 8 bits of the page frame number - * and store it in the page_key_data list of arrays. - */ -void page_key_memorize(unsigned long *pfn) -{ - page_key_wp->data[page_key_wx] = *(unsigned char *) pfn; - *(unsigned char *) pfn = 0; - if (++page_key_wx < PAGE_KEY_DATA_SIZE) - return; - page_key_wp = page_key_wp->next; - page_key_wx = 0; -} - -/* - * Get the next key from the page_key_data list of arrays and set the - * storage key of the page referred by @address. If @address refers to - * a "safe" page the swsusp_arch_resume code will transfer the storage - * key from the buffer page to the original page. - */ -void page_key_write(void *address) -{ - page_set_storage_key((unsigned long) address, - page_key_rp->data[page_key_rx], 0); - if (++page_key_rx >= PAGE_KEY_DATA_SIZE) - return; - page_key_rp = page_key_rp->next; - page_key_rx = 0; -} - -int pfn_is_nosave(unsigned long pfn) -{ - unsigned long nosave_begin_pfn = PFN_DOWN(__pa(&__nosave_begin)); - unsigned long nosave_end_pfn = PFN_DOWN(__pa(&__nosave_end)); - - /* Always save lowcore pages (LC protection might be enabled). */ - if (pfn <= LC_PAGES) - return 0; - if (pfn >= nosave_begin_pfn && pfn < nosave_end_pfn) - return 1; - /* Skip memory holes and read-only pages (NSS, DCSS, ...). */ - if (tprot(PFN_PHYS(pfn))) - return 1; - return 0; -} - -void save_processor_state(void) -{ - /* swsusp_arch_suspend() actually saves all cpu register contents. - * Machine checks must be disabled since swsusp_arch_suspend() stores - * register contents to their lowcore save areas. That's the same - * place where register contents on machine checks would be saved. - * To avoid register corruption disable machine checks. - * We must also disable machine checks in the new psw mask for - * program checks, since swsusp_arch_suspend() may generate program - * checks. Disabling machine checks for all other new psw masks is - * just paranoia. - */ - local_mcck_disable(); - /* Disable lowcore protection */ - __ctl_clear_bit(0,28); - S390_lowcore.external_new_psw.mask &= ~PSW_MASK_MCHECK; - S390_lowcore.svc_new_psw.mask &= ~PSW_MASK_MCHECK; - S390_lowcore.io_new_psw.mask &= ~PSW_MASK_MCHECK; - S390_lowcore.program_new_psw.mask &= ~PSW_MASK_MCHECK; -} - -void restore_processor_state(void) -{ - S390_lowcore.external_new_psw.mask |= PSW_MASK_MCHECK; - S390_lowcore.svc_new_psw.mask |= PSW_MASK_MCHECK; - S390_lowcore.io_new_psw.mask |= PSW_MASK_MCHECK; - S390_lowcore.program_new_psw.mask |= PSW_MASK_MCHECK; - /* Enable lowcore protection */ - __ctl_set_bit(0,28); - local_mcck_enable(); -} diff --git a/ANDROID_3.4.5/arch/s390/kernel/swsusp_asm64.S b/ANDROID_3.4.5/arch/s390/kernel/swsusp_asm64.S deleted file mode 100644 index dd70ef04..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/swsusp_asm64.S +++ /dev/null @@ -1,285 +0,0 @@ -/* - * S390 64-bit swsusp implementation - * - * Copyright IBM Corp. 2009 - * - * Author(s): Hans-Joachim Picht <hans@linux.vnet.ibm.com> - * Michael Holzheu <holzheu@linux.vnet.ibm.com> - */ - -#include <linux/linkage.h> -#include <asm/page.h> -#include <asm/ptrace.h> -#include <asm/thread_info.h> -#include <asm/asm-offsets.h> - -/* - * Save register context in absolute 0 lowcore and call swsusp_save() to - * create in-memory kernel image. The context is saved in the designated - * "store status" memory locations (see POP). - * We return from this function twice. The first time during the suspend to - * disk process. The second time via the swsusp_arch_resume() function - * (see below) in the resume process. - * This function runs with disabled interrupts. - */ - .section .text -ENTRY(swsusp_arch_suspend) - stmg %r6,%r15,__SF_GPRS(%r15) - lgr %r1,%r15 - aghi %r15,-STACK_FRAME_OVERHEAD - stg %r1,__SF_BACKCHAIN(%r15) - - /* Deactivate DAT */ - stnsm __SF_EMPTY(%r15),0xfb - - /* Store prefix register on stack */ - stpx __SF_EMPTY(%r15) - - /* Save prefix register contents for lowcore */ - llgf %r4,__SF_EMPTY(%r15) - - /* Get pointer to save area */ - lghi %r1,0x1000 - - /* Save CPU address */ - stap __LC_EXT_CPU_ADDR(%r0) - - /* Store registers */ - mvc 0x318(4,%r1),__SF_EMPTY(%r15) /* move prefix to lowcore */ - stfpc 0x31c(%r1) /* store fpu control */ - std 0,0x200(%r1) /* store f0 */ - std 1,0x208(%r1) /* store f1 */ - std 2,0x210(%r1) /* store f2 */ - std 3,0x218(%r1) /* store f3 */ - std 4,0x220(%r1) /* store f4 */ - std 5,0x228(%r1) /* store f5 */ - std 6,0x230(%r1) /* store f6 */ - std 7,0x238(%r1) /* store f7 */ - std 8,0x240(%r1) /* store f8 */ - std 9,0x248(%r1) /* store f9 */ - std 10,0x250(%r1) /* store f10 */ - std 11,0x258(%r1) /* store f11 */ - std 12,0x260(%r1) /* store f12 */ - std 13,0x268(%r1) /* store f13 */ - std 14,0x270(%r1) /* store f14 */ - std 15,0x278(%r1) /* store f15 */ - stam %a0,%a15,0x340(%r1) /* store access registers */ - stctg %c0,%c15,0x380(%r1) /* store control registers */ - stmg %r0,%r15,0x280(%r1) /* store general registers */ - - stpt 0x328(%r1) /* store timer */ - stck __SF_EMPTY(%r15) /* store clock */ - stckc 0x330(%r1) /* store clock comparator */ - - /* Update cputime accounting before going to sleep */ - lg %r0,__LC_LAST_UPDATE_TIMER - slg %r0,0x328(%r1) - alg %r0,__LC_SYSTEM_TIMER - stg %r0,__LC_SYSTEM_TIMER - mvc __LC_LAST_UPDATE_TIMER(8),0x328(%r1) - lg %r0,__LC_LAST_UPDATE_CLOCK - slg %r0,__SF_EMPTY(%r15) - alg %r0,__LC_STEAL_TIMER - stg %r0,__LC_STEAL_TIMER - mvc __LC_LAST_UPDATE_CLOCK(8),__SF_EMPTY(%r15) - - /* Activate DAT */ - stosm __SF_EMPTY(%r15),0x04 - - /* Set prefix page to zero */ - xc __SF_EMPTY(4,%r15),__SF_EMPTY(%r15) - spx __SF_EMPTY(%r15) - - lghi %r2,0 - lghi %r3,2*PAGE_SIZE - lghi %r5,2*PAGE_SIZE -1: mvcle %r2,%r4,0 - jo 1b - - /* Save image */ - brasl %r14,swsusp_save - - /* Restore prefix register and return */ - lghi %r1,0x1000 - spx 0x318(%r1) - lmg %r6,%r15,STACK_FRAME_OVERHEAD + __SF_GPRS(%r15) - lghi %r2,0 - br %r14 - -/* - * Restore saved memory image to correct place and restore register context. - * Then we return to the function that called swsusp_arch_suspend(). - * swsusp_arch_resume() runs with disabled interrupts. - */ -ENTRY(swsusp_arch_resume) - stmg %r6,%r15,__SF_GPRS(%r15) - lgr %r1,%r15 - aghi %r15,-STACK_FRAME_OVERHEAD - stg %r1,__SF_BACKCHAIN(%r15) - - /* Make all free pages stable */ - lghi %r2,1 - brasl %r14,arch_set_page_states - - /* Deactivate DAT */ - stnsm __SF_EMPTY(%r15),0xfb - - /* Set prefix page to zero */ - xc __SF_EMPTY(4,%r15),__SF_EMPTY(%r15) - spx __SF_EMPTY(%r15) - - /* Restore saved image */ - larl %r1,restore_pblist - lg %r1,0(%r1) - ltgr %r1,%r1 - jz 2f -0: - lg %r2,8(%r1) - lg %r4,0(%r1) - iske %r0,%r4 - lghi %r3,PAGE_SIZE - lghi %r5,PAGE_SIZE -1: - mvcle %r2,%r4,0 - jo 1b - lg %r2,8(%r1) - sske %r0,%r2 - lg %r1,16(%r1) - ltgr %r1,%r1 - jnz 0b -2: - ptlb /* flush tlb */ - - /* Reset System */ - larl %r1,restart_entry - larl %r2,.Lrestart_diag308_psw - og %r1,0(%r2) - stg %r1,0(%r0) - larl %r1,.Lnew_pgm_check_psw - epsw %r2,%r3 - stm %r2,%r3,0(%r1) - mvc __LC_PGM_NEW_PSW(16,%r0),0(%r1) - lghi %r0,0 - diag %r0,%r0,0x308 -restart_entry: - lhi %r1,1 - sigp %r1,%r0,0x12 - sam64 - larl %r1,.Lnew_pgm_check_psw - lpswe 0(%r1) -pgm_check_entry: - - /* Switch to original suspend CPU */ - larl %r1,.Lresume_cpu /* Resume CPU address: r2 */ - stap 0(%r1) - llgh %r2,0(%r1) - llgh %r1,__LC_EXT_CPU_ADDR(%r0) /* Suspend CPU address: r1 */ - cgr %r1,%r2 - je restore_registers /* r1 = r2 -> nothing to do */ - larl %r4,.Lrestart_suspend_psw /* Set new restart PSW */ - mvc __LC_RST_NEW_PSW(16,%r0),0(%r4) -3: - sigp %r9,%r1,11 /* sigp initial cpu reset */ - brc 8,4f /* accepted */ - brc 2,3b /* busy, try again */ - - /* Suspend CPU not available -> panic */ - larl %r15,init_thread_union - ahi %r15,1<<(PAGE_SHIFT+THREAD_ORDER) - larl %r2,.Lpanic_string - larl %r3,_sclp_print_early - lghi %r1,0 - sam31 - sigp %r1,%r0,0x12 - basr %r14,%r3 - larl %r3,.Ldisabled_wait_31 - lpsw 0(%r3) -4: - /* Switch to suspend CPU */ - sigp %r9,%r1,6 /* sigp restart to suspend CPU */ - brc 2,4b /* busy, try again */ -5: - sigp %r9,%r2,5 /* sigp stop to current resume CPU */ - brc 2,5b /* busy, try again */ -6: j 6b - -restart_suspend: - larl %r1,.Lresume_cpu - llgh %r2,0(%r1) -7: - sigp %r9,%r2,1 /* sigp sense, wait for resume CPU */ - brc 8,7b /* accepted, status 0, still running */ - brc 2,7b /* busy, try again */ - tmll %r9,0x40 /* Test if resume CPU is stopped */ - jz 7b - -restore_registers: - /* Restore registers */ - lghi %r13,0x1000 /* %r1 = pointer to save area */ - - /* Ignore time spent in suspended state. */ - llgf %r1,0x318(%r13) - stck __LC_LAST_UPDATE_CLOCK(%r1) - spt 0x328(%r13) /* reprogram timer */ - //sckc 0x330(%r13) /* set clock comparator */ - - lctlg %c0,%c15,0x380(%r13) /* load control registers */ - lam %a0,%a15,0x340(%r13) /* load access registers */ - - lfpc 0x31c(%r13) /* load fpu control */ - ld 0,0x200(%r13) /* load f0 */ - ld 1,0x208(%r13) /* load f1 */ - ld 2,0x210(%r13) /* load f2 */ - ld 3,0x218(%r13) /* load f3 */ - ld 4,0x220(%r13) /* load f4 */ - ld 5,0x228(%r13) /* load f5 */ - ld 6,0x230(%r13) /* load f6 */ - ld 7,0x238(%r13) /* load f7 */ - ld 8,0x240(%r13) /* load f8 */ - ld 9,0x248(%r13) /* load f9 */ - ld 10,0x250(%r13) /* load f10 */ - ld 11,0x258(%r13) /* load f11 */ - ld 12,0x260(%r13) /* load f12 */ - ld 13,0x268(%r13) /* load f13 */ - ld 14,0x270(%r13) /* load f14 */ - ld 15,0x278(%r13) /* load f15 */ - - /* Load old stack */ - lg %r15,0x2f8(%r13) - - /* Restore prefix register */ - spx 0x318(%r13) - - /* Activate DAT */ - stosm __SF_EMPTY(%r15),0x04 - - /* Make all free pages unstable */ - lghi %r2,0 - brasl %r14,arch_set_page_states - - /* Log potential guest relocation */ - brasl %r14,lgr_info_log - - /* Reinitialize the channel subsystem */ - brasl %r14,channel_subsystem_reinit - - /* Return 0 */ - lmg %r6,%r15,STACK_FRAME_OVERHEAD + __SF_GPRS(%r15) - lghi %r2,0 - br %r14 - - .section .data..nosave,"aw",@progbits - .align 8 -.Ldisabled_wait_31: - .long 0x000a0000,0x00000000 -.Lpanic_string: - .asciz "Resume not possible because suspend CPU is no longer available" - .align 8 -.Lrestart_diag308_psw: - .long 0x00080000,0x80000000 -.Lrestart_suspend_psw: - .quad 0x0000000180000000,restart_suspend -.Lnew_pgm_check_psw: - .quad 0,pgm_check_entry -.Lresume_cpu: - .byte 0,0 diff --git a/ANDROID_3.4.5/arch/s390/kernel/sys_s390.c b/ANDROID_3.4.5/arch/s390/kernel/sys_s390.c deleted file mode 100644 index 78ea1948..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/sys_s390.c +++ /dev/null @@ -1,151 +0,0 @@ -/* - * arch/s390/kernel/sys_s390.c - * - * S390 version - * Copyright (C) 1999,2000 IBM Deutschland Entwicklung GmbH, IBM Corporation - * Author(s): Martin Schwidefsky (schwidefsky@de.ibm.com), - * Thomas Spatzier (tspat@de.ibm.com) - * - * Derived from "arch/i386/kernel/sys_i386.c" - * - * This file contains various random system calls that - * have a non-standard calling sequence on the Linux/s390 - * platform. - */ - -#include <linux/errno.h> -#include <linux/sched.h> -#include <linux/mm.h> -#include <linux/fs.h> -#include <linux/smp.h> -#include <linux/sem.h> -#include <linux/msg.h> -#include <linux/shm.h> -#include <linux/stat.h> -#include <linux/syscalls.h> -#include <linux/mman.h> -#include <linux/file.h> -#include <linux/utsname.h> -#include <linux/personality.h> -#include <linux/unistd.h> -#include <linux/ipc.h> -#include <asm/uaccess.h> -#include "entry.h" - -/* - * Perform the mmap() system call. Linux for S/390 isn't able to handle more - * than 5 system call parameters, so this system call uses a memory block - * for parameter passing. - */ - -struct s390_mmap_arg_struct { - unsigned long addr; - unsigned long len; - unsigned long prot; - unsigned long flags; - unsigned long fd; - unsigned long offset; -}; - -SYSCALL_DEFINE1(mmap2, struct s390_mmap_arg_struct __user *, arg) -{ - struct s390_mmap_arg_struct a; - int error = -EFAULT; - - if (copy_from_user(&a, arg, sizeof(a))) - goto out; - error = sys_mmap_pgoff(a.addr, a.len, a.prot, a.flags, a.fd, a.offset); -out: - return error; -} - -/* - * sys_ipc() is the de-multiplexer for the SysV IPC calls. - */ -SYSCALL_DEFINE5(s390_ipc, uint, call, int, first, unsigned long, second, - unsigned long, third, void __user *, ptr) -{ - if (call >> 16) - return -EINVAL; - /* The s390 sys_ipc variant has only five parameters instead of six - * like the generic variant. The only difference is the handling of - * the SEMTIMEDOP subcall where on s390 the third parameter is used - * as a pointer to a struct timespec where the generic variant uses - * the fifth parameter. - * Therefore we can call the generic variant by simply passing the - * third parameter also as fifth parameter. - */ - return sys_ipc(call, first, second, third, ptr, third); -} - -#ifdef CONFIG_64BIT -SYSCALL_DEFINE1(s390_personality, unsigned int, personality) -{ - unsigned int ret; - - if (current->personality == PER_LINUX32 && personality == PER_LINUX) - personality = PER_LINUX32; - ret = sys_personality(personality); - if (ret == PER_LINUX32) - ret = PER_LINUX; - - return ret; -} -#endif /* CONFIG_64BIT */ - -/* - * Wrapper function for sys_fadvise64/fadvise64_64 - */ -#ifndef CONFIG_64BIT - -SYSCALL_DEFINE5(s390_fadvise64, int, fd, u32, offset_high, u32, offset_low, - size_t, len, int, advice) -{ - return sys_fadvise64(fd, (u64) offset_high << 32 | offset_low, - len, advice); -} - -struct fadvise64_64_args { - int fd; - long long offset; - long long len; - int advice; -}; - -SYSCALL_DEFINE1(s390_fadvise64_64, struct fadvise64_64_args __user *, args) -{ - struct fadvise64_64_args a; - - if ( copy_from_user(&a, args, sizeof(a)) ) - return -EFAULT; - return sys_fadvise64_64(a.fd, a.offset, a.len, a.advice); -} - -/* - * This is a wrapper to call sys_fallocate(). For 31 bit s390 the last - * 64 bit argument "len" is split into the upper and lower 32 bits. The - * system call wrapper in the user space loads the value to %r6/%r7. - * The code in entry.S keeps the values in %r2 - %r6 where they are and - * stores %r7 to 96(%r15). But the standard C linkage requires that - * the whole 64 bit value for len is stored on the stack and doesn't - * use %r6 at all. So s390_fallocate has to convert the arguments from - * %r2: fd, %r3: mode, %r4/%r5: offset, %r6/96(%r15)-99(%r15): len - * to - * %r2: fd, %r3: mode, %r4/%r5: offset, 96(%r15)-103(%r15): len - */ -SYSCALL_DEFINE(s390_fallocate)(int fd, int mode, loff_t offset, - u32 len_high, u32 len_low) -{ - return sys_fallocate(fd, mode, offset, ((u64)len_high << 32) | len_low); -} -#ifdef CONFIG_HAVE_SYSCALL_WRAPPERS -asmlinkage long SyS_s390_fallocate(long fd, long mode, loff_t offset, - long len_high, long len_low) -{ - return SYSC_s390_fallocate((int) fd, (int) mode, offset, - (u32) len_high, (u32) len_low); -} -SYSCALL_ALIAS(sys_s390_fallocate, SyS_s390_fallocate); -#endif - -#endif diff --git a/ANDROID_3.4.5/arch/s390/kernel/syscalls.S b/ANDROID_3.4.5/arch/s390/kernel/syscalls.S deleted file mode 100644 index bcab2f04..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/syscalls.S +++ /dev/null @@ -1,352 +0,0 @@ -/* - * definitions for sys_call_table, each line represents an - * entry in the table in the form - * SYSCALL(31 bit syscall, 64 bit syscall, 31 bit emulated syscall) - * - * this file is meant to be included from entry.S and entry64.S - */ - -#define NI_SYSCALL SYSCALL(sys_ni_syscall,sys_ni_syscall,sys_ni_syscall) - -NI_SYSCALL /* 0 */ -SYSCALL(sys_exit,sys_exit,sys32_exit_wrapper) -SYSCALL(sys_fork,sys_fork,sys_fork) -SYSCALL(sys_read,sys_read,sys32_read_wrapper) -SYSCALL(sys_write,sys_write,sys32_write_wrapper) -SYSCALL(sys_open,sys_open,sys32_open_wrapper) /* 5 */ -SYSCALL(sys_close,sys_close,sys32_close_wrapper) -SYSCALL(sys_restart_syscall,sys_restart_syscall,sys_restart_syscall) -SYSCALL(sys_creat,sys_creat,sys32_creat_wrapper) -SYSCALL(sys_link,sys_link,sys32_link_wrapper) -SYSCALL(sys_unlink,sys_unlink,sys32_unlink_wrapper) /* 10 */ -SYSCALL(sys_execve,sys_execve,sys32_execve_wrapper) -SYSCALL(sys_chdir,sys_chdir,sys32_chdir_wrapper) -SYSCALL(sys_time,sys_ni_syscall,sys32_time_wrapper) /* old time syscall */ -SYSCALL(sys_mknod,sys_mknod,sys32_mknod_wrapper) -SYSCALL(sys_chmod,sys_chmod,sys32_chmod_wrapper) /* 15 */ -SYSCALL(sys_lchown16,sys_ni_syscall,sys32_lchown16_wrapper) /* old lchown16 syscall*/ -NI_SYSCALL /* old break syscall holder */ -NI_SYSCALL /* old stat syscall holder */ -SYSCALL(sys_lseek,sys_lseek,sys32_lseek_wrapper) -SYSCALL(sys_getpid,sys_getpid,sys_getpid) /* 20 */ -SYSCALL(sys_mount,sys_mount,sys32_mount_wrapper) -SYSCALL(sys_oldumount,sys_oldumount,sys32_oldumount_wrapper) -SYSCALL(sys_setuid16,sys_ni_syscall,sys32_setuid16_wrapper) /* old setuid16 syscall*/ -SYSCALL(sys_getuid16,sys_ni_syscall,sys32_getuid16) /* old getuid16 syscall*/ -SYSCALL(sys_stime,sys_ni_syscall,sys32_stime_wrapper) /* 25 old stime syscall */ -SYSCALL(sys_ptrace,sys_ptrace,sys32_ptrace_wrapper) -SYSCALL(sys_alarm,sys_alarm,sys32_alarm_wrapper) -NI_SYSCALL /* old fstat syscall */ -SYSCALL(sys_pause,sys_pause,sys_pause) -SYSCALL(sys_utime,sys_utime,compat_sys_utime_wrapper) /* 30 */ -NI_SYSCALL /* old stty syscall */ -NI_SYSCALL /* old gtty syscall */ -SYSCALL(sys_access,sys_access,sys32_access_wrapper) -SYSCALL(sys_nice,sys_nice,sys32_nice_wrapper) -NI_SYSCALL /* 35 old ftime syscall */ -SYSCALL(sys_sync,sys_sync,sys_sync) -SYSCALL(sys_kill,sys_kill,sys32_kill_wrapper) -SYSCALL(sys_rename,sys_rename,sys32_rename_wrapper) -SYSCALL(sys_mkdir,sys_mkdir,sys32_mkdir_wrapper) -SYSCALL(sys_rmdir,sys_rmdir,sys32_rmdir_wrapper) /* 40 */ -SYSCALL(sys_dup,sys_dup,sys32_dup_wrapper) -SYSCALL(sys_pipe,sys_pipe,sys32_pipe_wrapper) -SYSCALL(sys_times,sys_times,compat_sys_times_wrapper) -NI_SYSCALL /* old prof syscall */ -SYSCALL(sys_brk,sys_brk,sys32_brk_wrapper) /* 45 */ -SYSCALL(sys_setgid16,sys_ni_syscall,sys32_setgid16_wrapper) /* old setgid16 syscall*/ -SYSCALL(sys_getgid16,sys_ni_syscall,sys32_getgid16) /* old getgid16 syscall*/ -SYSCALL(sys_signal,sys_signal,sys32_signal_wrapper) -SYSCALL(sys_geteuid16,sys_ni_syscall,sys32_geteuid16) /* old geteuid16 syscall */ -SYSCALL(sys_getegid16,sys_ni_syscall,sys32_getegid16) /* 50 old getegid16 syscall */ -SYSCALL(sys_acct,sys_acct,sys32_acct_wrapper) -SYSCALL(sys_umount,sys_umount,sys32_umount_wrapper) -NI_SYSCALL /* old lock syscall */ -SYSCALL(sys_ioctl,sys_ioctl,compat_sys_ioctl_wrapper) -SYSCALL(sys_fcntl,sys_fcntl,compat_sys_fcntl_wrapper) /* 55 */ -NI_SYSCALL /* intel mpx syscall */ -SYSCALL(sys_setpgid,sys_setpgid,sys32_setpgid_wrapper) -NI_SYSCALL /* old ulimit syscall */ -NI_SYSCALL /* old uname syscall */ -SYSCALL(sys_umask,sys_umask,sys32_umask_wrapper) /* 60 */ -SYSCALL(sys_chroot,sys_chroot,sys32_chroot_wrapper) -SYSCALL(sys_ustat,sys_ustat,sys32_ustat_wrapper) -SYSCALL(sys_dup2,sys_dup2,sys32_dup2_wrapper) -SYSCALL(sys_getppid,sys_getppid,sys_getppid) -SYSCALL(sys_getpgrp,sys_getpgrp,sys_getpgrp) /* 65 */ -SYSCALL(sys_setsid,sys_setsid,sys_setsid) -SYSCALL(sys_sigaction,sys_sigaction,sys32_sigaction_wrapper) -NI_SYSCALL /* old sgetmask syscall*/ -NI_SYSCALL /* old ssetmask syscall*/ -SYSCALL(sys_setreuid16,sys_ni_syscall,sys32_setreuid16_wrapper) /* old setreuid16 syscall */ -SYSCALL(sys_setregid16,sys_ni_syscall,sys32_setregid16_wrapper) /* old setregid16 syscall */ -SYSCALL(sys_sigsuspend,sys_sigsuspend,sys_sigsuspend_wrapper) -SYSCALL(sys_sigpending,sys_sigpending,compat_sys_sigpending_wrapper) -SYSCALL(sys_sethostname,sys_sethostname,sys32_sethostname_wrapper) -SYSCALL(sys_setrlimit,sys_setrlimit,compat_sys_setrlimit_wrapper) /* 75 */ -SYSCALL(sys_old_getrlimit,sys_getrlimit,compat_sys_old_getrlimit_wrapper) -SYSCALL(sys_getrusage,sys_getrusage,compat_sys_getrusage_wrapper) -SYSCALL(sys_gettimeofday,sys_gettimeofday,compat_sys_gettimeofday_wrapper) -SYSCALL(sys_settimeofday,sys_settimeofday,compat_sys_settimeofday_wrapper) -SYSCALL(sys_getgroups16,sys_ni_syscall,sys32_getgroups16_wrapper) /* 80 old getgroups16 syscall */ -SYSCALL(sys_setgroups16,sys_ni_syscall,sys32_setgroups16_wrapper) /* old setgroups16 syscall */ -NI_SYSCALL /* old select syscall */ -SYSCALL(sys_symlink,sys_symlink,sys32_symlink_wrapper) -NI_SYSCALL /* old lstat syscall */ -SYSCALL(sys_readlink,sys_readlink,sys32_readlink_wrapper) /* 85 */ -SYSCALL(sys_uselib,sys_uselib,sys32_uselib_wrapper) -SYSCALL(sys_swapon,sys_swapon,sys32_swapon_wrapper) -SYSCALL(sys_reboot,sys_reboot,sys32_reboot_wrapper) -SYSCALL(sys_ni_syscall,sys_ni_syscall,old32_readdir_wrapper) /* old readdir syscall */ -SYSCALL(sys_old_mmap,sys_old_mmap,old32_mmap_wrapper) /* 90 */ -SYSCALL(sys_munmap,sys_munmap,sys32_munmap_wrapper) -SYSCALL(sys_truncate,sys_truncate,sys32_truncate_wrapper) -SYSCALL(sys_ftruncate,sys_ftruncate,sys32_ftruncate_wrapper) -SYSCALL(sys_fchmod,sys_fchmod,sys32_fchmod_wrapper) -SYSCALL(sys_fchown16,sys_ni_syscall,sys32_fchown16_wrapper) /* 95 old fchown16 syscall*/ -SYSCALL(sys_getpriority,sys_getpriority,sys32_getpriority_wrapper) -SYSCALL(sys_setpriority,sys_setpriority,sys32_setpriority_wrapper) -NI_SYSCALL /* old profil syscall */ -SYSCALL(sys_statfs,sys_statfs,compat_sys_statfs_wrapper) -SYSCALL(sys_fstatfs,sys_fstatfs,compat_sys_fstatfs_wrapper) /* 100 */ -NI_SYSCALL /* ioperm for i386 */ -SYSCALL(sys_socketcall,sys_socketcall,compat_sys_socketcall_wrapper) -SYSCALL(sys_syslog,sys_syslog,sys32_syslog_wrapper) -SYSCALL(sys_setitimer,sys_setitimer,compat_sys_setitimer_wrapper) -SYSCALL(sys_getitimer,sys_getitimer,compat_sys_getitimer_wrapper) /* 105 */ -SYSCALL(sys_newstat,sys_newstat,compat_sys_newstat_wrapper) -SYSCALL(sys_newlstat,sys_newlstat,compat_sys_newlstat_wrapper) -SYSCALL(sys_newfstat,sys_newfstat,compat_sys_newfstat_wrapper) -NI_SYSCALL /* old uname syscall */ -SYSCALL(sys_lookup_dcookie,sys_lookup_dcookie,sys32_lookup_dcookie_wrapper) /* 110 */ -SYSCALL(sys_vhangup,sys_vhangup,sys_vhangup) -NI_SYSCALL /* old "idle" system call */ -NI_SYSCALL /* vm86old for i386 */ -SYSCALL(sys_wait4,sys_wait4,compat_sys_wait4_wrapper) -SYSCALL(sys_swapoff,sys_swapoff,sys32_swapoff_wrapper) /* 115 */ -SYSCALL(sys_sysinfo,sys_sysinfo,compat_sys_sysinfo_wrapper) -SYSCALL(sys_s390_ipc,sys_s390_ipc,sys32_ipc_wrapper) -SYSCALL(sys_fsync,sys_fsync,sys32_fsync_wrapper) -SYSCALL(sys_sigreturn,sys_sigreturn,sys32_sigreturn) -SYSCALL(sys_clone,sys_clone,sys_clone_wrapper) /* 120 */ -SYSCALL(sys_setdomainname,sys_setdomainname,sys32_setdomainname_wrapper) -SYSCALL(sys_newuname,sys_newuname,sys32_newuname_wrapper) -NI_SYSCALL /* modify_ldt for i386 */ -SYSCALL(sys_adjtimex,sys_adjtimex,compat_sys_adjtimex_wrapper) -SYSCALL(sys_mprotect,sys_mprotect,sys32_mprotect_wrapper) /* 125 */ -SYSCALL(sys_sigprocmask,sys_sigprocmask,compat_sys_sigprocmask_wrapper) -NI_SYSCALL /* old "create module" */ -SYSCALL(sys_init_module,sys_init_module,sys_init_module_wrapper) -SYSCALL(sys_delete_module,sys_delete_module,sys_delete_module_wrapper) -NI_SYSCALL /* 130: old get_kernel_syms */ -SYSCALL(sys_quotactl,sys_quotactl,sys32_quotactl_wrapper) -SYSCALL(sys_getpgid,sys_getpgid,sys32_getpgid_wrapper) -SYSCALL(sys_fchdir,sys_fchdir,sys32_fchdir_wrapper) -SYSCALL(sys_bdflush,sys_bdflush,sys32_bdflush_wrapper) -SYSCALL(sys_sysfs,sys_sysfs,sys32_sysfs_wrapper) /* 135 */ -SYSCALL(sys_personality,sys_s390_personality,sys32_personality_wrapper) -NI_SYSCALL /* for afs_syscall */ -SYSCALL(sys_setfsuid16,sys_ni_syscall,sys32_setfsuid16_wrapper) /* old setfsuid16 syscall */ -SYSCALL(sys_setfsgid16,sys_ni_syscall,sys32_setfsgid16_wrapper) /* old setfsgid16 syscall */ -SYSCALL(sys_llseek,sys_llseek,sys32_llseek_wrapper) /* 140 */ -SYSCALL(sys_getdents,sys_getdents,sys32_getdents_wrapper) -SYSCALL(sys_select,sys_select,compat_sys_select_wrapper) -SYSCALL(sys_flock,sys_flock,sys32_flock_wrapper) -SYSCALL(sys_msync,sys_msync,sys32_msync_wrapper) -SYSCALL(sys_readv,sys_readv,compat_sys_readv_wrapper) /* 145 */ -SYSCALL(sys_writev,sys_writev,compat_sys_writev_wrapper) -SYSCALL(sys_getsid,sys_getsid,sys32_getsid_wrapper) -SYSCALL(sys_fdatasync,sys_fdatasync,sys32_fdatasync_wrapper) -SYSCALL(sys_sysctl,sys_sysctl,sys32_sysctl_wrapper) -SYSCALL(sys_mlock,sys_mlock,sys32_mlock_wrapper) /* 150 */ -SYSCALL(sys_munlock,sys_munlock,sys32_munlock_wrapper) -SYSCALL(sys_mlockall,sys_mlockall,sys32_mlockall_wrapper) -SYSCALL(sys_munlockall,sys_munlockall,sys_munlockall) -SYSCALL(sys_sched_setparam,sys_sched_setparam,sys32_sched_setparam_wrapper) -SYSCALL(sys_sched_getparam,sys_sched_getparam,sys32_sched_getparam_wrapper) /* 155 */ -SYSCALL(sys_sched_setscheduler,sys_sched_setscheduler,sys32_sched_setscheduler_wrapper) -SYSCALL(sys_sched_getscheduler,sys_sched_getscheduler,sys32_sched_getscheduler_wrapper) -SYSCALL(sys_sched_yield,sys_sched_yield,sys_sched_yield) -SYSCALL(sys_sched_get_priority_max,sys_sched_get_priority_max,sys32_sched_get_priority_max_wrapper) -SYSCALL(sys_sched_get_priority_min,sys_sched_get_priority_min,sys32_sched_get_priority_min_wrapper) /* 160 */ -SYSCALL(sys_sched_rr_get_interval,sys_sched_rr_get_interval,sys32_sched_rr_get_interval_wrapper) -SYSCALL(sys_nanosleep,sys_nanosleep,compat_sys_nanosleep_wrapper) -SYSCALL(sys_mremap,sys_mremap,sys32_mremap_wrapper) -SYSCALL(sys_setresuid16,sys_ni_syscall,sys32_setresuid16_wrapper) /* old setresuid16 syscall */ -SYSCALL(sys_getresuid16,sys_ni_syscall,sys32_getresuid16_wrapper) /* 165 old getresuid16 syscall */ -NI_SYSCALL /* for vm86 */ -NI_SYSCALL /* old sys_query_module */ -SYSCALL(sys_poll,sys_poll,sys32_poll_wrapper) -NI_SYSCALL /* old nfsservctl */ -SYSCALL(sys_setresgid16,sys_ni_syscall,sys32_setresgid16_wrapper) /* 170 old setresgid16 syscall */ -SYSCALL(sys_getresgid16,sys_ni_syscall,sys32_getresgid16_wrapper) /* old getresgid16 syscall */ -SYSCALL(sys_prctl,sys_prctl,sys32_prctl_wrapper) -SYSCALL(sys_rt_sigreturn,sys_rt_sigreturn,sys32_rt_sigreturn) -SYSCALL(sys_rt_sigaction,sys_rt_sigaction,sys32_rt_sigaction_wrapper) -SYSCALL(sys_rt_sigprocmask,sys_rt_sigprocmask,sys32_rt_sigprocmask_wrapper) /* 175 */ -SYSCALL(sys_rt_sigpending,sys_rt_sigpending,sys32_rt_sigpending_wrapper) -SYSCALL(sys_rt_sigtimedwait,sys_rt_sigtimedwait,compat_sys_rt_sigtimedwait_wrapper) -SYSCALL(sys_rt_sigqueueinfo,sys_rt_sigqueueinfo,sys32_rt_sigqueueinfo_wrapper) -SYSCALL(sys_rt_sigsuspend,sys_rt_sigsuspend,compat_sys_rt_sigsuspend_wrapper) -SYSCALL(sys_pread64,sys_pread64,sys32_pread64_wrapper) /* 180 */ -SYSCALL(sys_pwrite64,sys_pwrite64,sys32_pwrite64_wrapper) -SYSCALL(sys_chown16,sys_ni_syscall,sys32_chown16_wrapper) /* old chown16 syscall */ -SYSCALL(sys_getcwd,sys_getcwd,sys32_getcwd_wrapper) -SYSCALL(sys_capget,sys_capget,sys32_capget_wrapper) -SYSCALL(sys_capset,sys_capset,sys32_capset_wrapper) /* 185 */ -SYSCALL(sys_sigaltstack,sys_sigaltstack,sys32_sigaltstack_wrapper) -SYSCALL(sys_sendfile,sys_sendfile64,sys32_sendfile_wrapper) -NI_SYSCALL /* streams1 */ -NI_SYSCALL /* streams2 */ -SYSCALL(sys_vfork,sys_vfork,sys_vfork) /* 190 */ -SYSCALL(sys_getrlimit,sys_getrlimit,compat_sys_getrlimit_wrapper) -SYSCALL(sys_mmap2,sys_mmap2,sys32_mmap2_wrapper) -SYSCALL(sys_truncate64,sys_ni_syscall,sys32_truncate64_wrapper) -SYSCALL(sys_ftruncate64,sys_ni_syscall,sys32_ftruncate64_wrapper) -SYSCALL(sys_stat64,sys_ni_syscall,sys32_stat64_wrapper) /* 195 */ -SYSCALL(sys_lstat64,sys_ni_syscall,sys32_lstat64_wrapper) -SYSCALL(sys_fstat64,sys_ni_syscall,sys32_fstat64_wrapper) -SYSCALL(sys_lchown,sys_lchown,sys32_lchown_wrapper) -SYSCALL(sys_getuid,sys_getuid,sys_getuid) -SYSCALL(sys_getgid,sys_getgid,sys_getgid) /* 200 */ -SYSCALL(sys_geteuid,sys_geteuid,sys_geteuid) -SYSCALL(sys_getegid,sys_getegid,sys_getegid) -SYSCALL(sys_setreuid,sys_setreuid,sys32_setreuid_wrapper) -SYSCALL(sys_setregid,sys_setregid,sys32_setregid_wrapper) -SYSCALL(sys_getgroups,sys_getgroups,sys32_getgroups_wrapper) /* 205 */ -SYSCALL(sys_setgroups,sys_setgroups,sys32_setgroups_wrapper) -SYSCALL(sys_fchown,sys_fchown,sys32_fchown_wrapper) -SYSCALL(sys_setresuid,sys_setresuid,sys32_setresuid_wrapper) -SYSCALL(sys_getresuid,sys_getresuid,sys32_getresuid_wrapper) -SYSCALL(sys_setresgid,sys_setresgid,sys32_setresgid_wrapper) /* 210 */ -SYSCALL(sys_getresgid,sys_getresgid,sys32_getresgid_wrapper) -SYSCALL(sys_chown,sys_chown,sys32_chown_wrapper) -SYSCALL(sys_setuid,sys_setuid,sys32_setuid_wrapper) -SYSCALL(sys_setgid,sys_setgid,sys32_setgid_wrapper) -SYSCALL(sys_setfsuid,sys_setfsuid,sys32_setfsuid_wrapper) /* 215 */ -SYSCALL(sys_setfsgid,sys_setfsgid,sys32_setfsgid_wrapper) -SYSCALL(sys_pivot_root,sys_pivot_root,sys32_pivot_root_wrapper) -SYSCALL(sys_mincore,sys_mincore,sys32_mincore_wrapper) -SYSCALL(sys_madvise,sys_madvise,sys32_madvise_wrapper) -SYSCALL(sys_getdents64,sys_getdents64,sys32_getdents64_wrapper) /* 220 */ -SYSCALL(sys_fcntl64,sys_ni_syscall,compat_sys_fcntl64_wrapper) -SYSCALL(sys_readahead,sys_readahead,sys32_readahead_wrapper) -SYSCALL(sys_sendfile64,sys_ni_syscall,sys32_sendfile64_wrapper) -SYSCALL(sys_setxattr,sys_setxattr,sys32_setxattr_wrapper) -SYSCALL(sys_lsetxattr,sys_lsetxattr,sys32_lsetxattr_wrapper) /* 225 */ -SYSCALL(sys_fsetxattr,sys_fsetxattr,sys32_fsetxattr_wrapper) -SYSCALL(sys_getxattr,sys_getxattr,sys32_getxattr_wrapper) -SYSCALL(sys_lgetxattr,sys_lgetxattr,sys32_lgetxattr_wrapper) -SYSCALL(sys_fgetxattr,sys_fgetxattr,sys32_fgetxattr_wrapper) -SYSCALL(sys_listxattr,sys_listxattr,sys32_listxattr_wrapper) /* 230 */ -SYSCALL(sys_llistxattr,sys_llistxattr,sys32_llistxattr_wrapper) -SYSCALL(sys_flistxattr,sys_flistxattr,sys32_flistxattr_wrapper) -SYSCALL(sys_removexattr,sys_removexattr,sys32_removexattr_wrapper) -SYSCALL(sys_lremovexattr,sys_lremovexattr,sys32_lremovexattr_wrapper) -SYSCALL(sys_fremovexattr,sys_fremovexattr,sys32_fremovexattr_wrapper) /* 235 */ -SYSCALL(sys_gettid,sys_gettid,sys_gettid) -SYSCALL(sys_tkill,sys_tkill,sys_tkill_wrapper) -SYSCALL(sys_futex,sys_futex,compat_sys_futex_wrapper) -SYSCALL(sys_sched_setaffinity,sys_sched_setaffinity,sys32_sched_setaffinity_wrapper) -SYSCALL(sys_sched_getaffinity,sys_sched_getaffinity,sys32_sched_getaffinity_wrapper) /* 240 */ -SYSCALL(sys_tgkill,sys_tgkill,sys_tgkill_wrapper) -NI_SYSCALL /* reserved for TUX */ -SYSCALL(sys_io_setup,sys_io_setup,sys32_io_setup_wrapper) -SYSCALL(sys_io_destroy,sys_io_destroy,sys32_io_destroy_wrapper) -SYSCALL(sys_io_getevents,sys_io_getevents,sys32_io_getevents_wrapper) /* 245 */ -SYSCALL(sys_io_submit,sys_io_submit,sys32_io_submit_wrapper) -SYSCALL(sys_io_cancel,sys_io_cancel,sys32_io_cancel_wrapper) -SYSCALL(sys_exit_group,sys_exit_group,sys32_exit_group_wrapper) -SYSCALL(sys_epoll_create,sys_epoll_create,sys_epoll_create_wrapper) -SYSCALL(sys_epoll_ctl,sys_epoll_ctl,sys_epoll_ctl_wrapper) /* 250 */ -SYSCALL(sys_epoll_wait,sys_epoll_wait,sys_epoll_wait_wrapper) -SYSCALL(sys_set_tid_address,sys_set_tid_address,sys32_set_tid_address_wrapper) -SYSCALL(sys_s390_fadvise64,sys_fadvise64_64,sys32_fadvise64_wrapper) -SYSCALL(sys_timer_create,sys_timer_create,sys32_timer_create_wrapper) -SYSCALL(sys_timer_settime,sys_timer_settime,sys32_timer_settime_wrapper) /* 255 */ -SYSCALL(sys_timer_gettime,sys_timer_gettime,sys32_timer_gettime_wrapper) -SYSCALL(sys_timer_getoverrun,sys_timer_getoverrun,sys32_timer_getoverrun_wrapper) -SYSCALL(sys_timer_delete,sys_timer_delete,sys32_timer_delete_wrapper) -SYSCALL(sys_clock_settime,sys_clock_settime,sys32_clock_settime_wrapper) -SYSCALL(sys_clock_gettime,sys_clock_gettime,sys32_clock_gettime_wrapper) /* 260 */ -SYSCALL(sys_clock_getres,sys_clock_getres,sys32_clock_getres_wrapper) -SYSCALL(sys_clock_nanosleep,sys_clock_nanosleep,sys32_clock_nanosleep_wrapper) -NI_SYSCALL /* reserved for vserver */ -SYSCALL(sys_s390_fadvise64_64,sys_ni_syscall,sys32_fadvise64_64_wrapper) -SYSCALL(sys_statfs64,sys_statfs64,compat_sys_statfs64_wrapper) -SYSCALL(sys_fstatfs64,sys_fstatfs64,compat_sys_fstatfs64_wrapper) -SYSCALL(sys_remap_file_pages,sys_remap_file_pages,sys32_remap_file_pages_wrapper) -NI_SYSCALL /* 268 sys_mbind */ -NI_SYSCALL /* 269 sys_get_mempolicy */ -NI_SYSCALL /* 270 sys_set_mempolicy */ -SYSCALL(sys_mq_open,sys_mq_open,compat_sys_mq_open_wrapper) -SYSCALL(sys_mq_unlink,sys_mq_unlink,sys32_mq_unlink_wrapper) -SYSCALL(sys_mq_timedsend,sys_mq_timedsend,compat_sys_mq_timedsend_wrapper) -SYSCALL(sys_mq_timedreceive,sys_mq_timedreceive,compat_sys_mq_timedreceive_wrapper) -SYSCALL(sys_mq_notify,sys_mq_notify,compat_sys_mq_notify_wrapper) /* 275 */ -SYSCALL(sys_mq_getsetattr,sys_mq_getsetattr,compat_sys_mq_getsetattr_wrapper) -SYSCALL(sys_kexec_load,sys_kexec_load,compat_sys_kexec_load_wrapper) -SYSCALL(sys_add_key,sys_add_key,compat_sys_add_key_wrapper) -SYSCALL(sys_request_key,sys_request_key,compat_sys_request_key_wrapper) -SYSCALL(sys_keyctl,sys_keyctl,compat_sys_keyctl_wrapper) /* 280 */ -SYSCALL(sys_waitid,sys_waitid,compat_sys_waitid_wrapper) -SYSCALL(sys_ioprio_set,sys_ioprio_set,sys_ioprio_set_wrapper) -SYSCALL(sys_ioprio_get,sys_ioprio_get,sys_ioprio_get_wrapper) -SYSCALL(sys_inotify_init,sys_inotify_init,sys_inotify_init) -SYSCALL(sys_inotify_add_watch,sys_inotify_add_watch,sys_inotify_add_watch_wrapper) /* 285 */ -SYSCALL(sys_inotify_rm_watch,sys_inotify_rm_watch,sys_inotify_rm_watch_wrapper) -NI_SYSCALL /* 287 sys_migrate_pages */ -SYSCALL(sys_openat,sys_openat,compat_sys_openat_wrapper) -SYSCALL(sys_mkdirat,sys_mkdirat,sys_mkdirat_wrapper) -SYSCALL(sys_mknodat,sys_mknodat,sys_mknodat_wrapper) /* 290 */ -SYSCALL(sys_fchownat,sys_fchownat,sys_fchownat_wrapper) -SYSCALL(sys_futimesat,sys_futimesat,compat_sys_futimesat_wrapper) -SYSCALL(sys_fstatat64,sys_newfstatat,sys32_fstatat64_wrapper) -SYSCALL(sys_unlinkat,sys_unlinkat,sys_unlinkat_wrapper) -SYSCALL(sys_renameat,sys_renameat,sys_renameat_wrapper) /* 295 */ -SYSCALL(sys_linkat,sys_linkat,sys_linkat_wrapper) -SYSCALL(sys_symlinkat,sys_symlinkat,sys_symlinkat_wrapper) -SYSCALL(sys_readlinkat,sys_readlinkat,sys_readlinkat_wrapper) -SYSCALL(sys_fchmodat,sys_fchmodat,sys_fchmodat_wrapper) -SYSCALL(sys_faccessat,sys_faccessat,sys_faccessat_wrapper) /* 300 */ -SYSCALL(sys_pselect6,sys_pselect6,compat_sys_pselect6_wrapper) -SYSCALL(sys_ppoll,sys_ppoll,compat_sys_ppoll_wrapper) -SYSCALL(sys_unshare,sys_unshare,sys_unshare_wrapper) -SYSCALL(sys_set_robust_list,sys_set_robust_list,compat_sys_set_robust_list_wrapper) -SYSCALL(sys_get_robust_list,sys_get_robust_list,compat_sys_get_robust_list_wrapper) -SYSCALL(sys_splice,sys_splice,sys_splice_wrapper) -SYSCALL(sys_sync_file_range,sys_sync_file_range,sys_sync_file_range_wrapper) -SYSCALL(sys_tee,sys_tee,sys_tee_wrapper) -SYSCALL(sys_vmsplice,sys_vmsplice,compat_sys_vmsplice_wrapper) -NI_SYSCALL /* 310 sys_move_pages */ -SYSCALL(sys_getcpu,sys_getcpu,sys_getcpu_wrapper) -SYSCALL(sys_epoll_pwait,sys_epoll_pwait,compat_sys_epoll_pwait_wrapper) -SYSCALL(sys_utimes,sys_utimes,compat_sys_utimes_wrapper) -SYSCALL(sys_s390_fallocate,sys_fallocate,sys_fallocate_wrapper) -SYSCALL(sys_utimensat,sys_utimensat,compat_sys_utimensat_wrapper) /* 315 */ -SYSCALL(sys_signalfd,sys_signalfd,compat_sys_signalfd_wrapper) -NI_SYSCALL /* 317 old sys_timer_fd */ -SYSCALL(sys_eventfd,sys_eventfd,sys_eventfd_wrapper) -SYSCALL(sys_timerfd_create,sys_timerfd_create,sys_timerfd_create_wrapper) -SYSCALL(sys_timerfd_settime,sys_timerfd_settime,compat_sys_timerfd_settime_wrapper) /* 320 */ -SYSCALL(sys_timerfd_gettime,sys_timerfd_gettime,compat_sys_timerfd_gettime_wrapper) -SYSCALL(sys_signalfd4,sys_signalfd4,compat_sys_signalfd4_wrapper) -SYSCALL(sys_eventfd2,sys_eventfd2,sys_eventfd2_wrapper) -SYSCALL(sys_inotify_init1,sys_inotify_init1,sys_inotify_init1_wrapper) -SYSCALL(sys_pipe2,sys_pipe2,sys_pipe2_wrapper) /* 325 */ -SYSCALL(sys_dup3,sys_dup3,sys_dup3_wrapper) -SYSCALL(sys_epoll_create1,sys_epoll_create1,sys_epoll_create1_wrapper) -SYSCALL(sys_preadv,sys_preadv,compat_sys_preadv_wrapper) -SYSCALL(sys_pwritev,sys_pwritev,compat_sys_pwritev_wrapper) -SYSCALL(sys_rt_tgsigqueueinfo,sys_rt_tgsigqueueinfo,compat_sys_rt_tgsigqueueinfo_wrapper) /* 330 */ -SYSCALL(sys_perf_event_open,sys_perf_event_open,sys_perf_event_open_wrapper) -SYSCALL(sys_fanotify_init,sys_fanotify_init,sys_fanotify_init_wrapper) -SYSCALL(sys_fanotify_mark,sys_fanotify_mark,sys_fanotify_mark_wrapper) -SYSCALL(sys_prlimit64,sys_prlimit64,sys_prlimit64_wrapper) -SYSCALL(sys_name_to_handle_at,sys_name_to_handle_at,sys_name_to_handle_at_wrapper) /* 335 */ -SYSCALL(sys_open_by_handle_at,sys_open_by_handle_at,compat_sys_open_by_handle_at_wrapper) -SYSCALL(sys_clock_adjtime,sys_clock_adjtime,compat_sys_clock_adjtime_wrapper) -SYSCALL(sys_syncfs,sys_syncfs,sys_syncfs_wrapper) -SYSCALL(sys_setns,sys_setns,sys_setns_wrapper) -SYSCALL(sys_process_vm_readv,sys_process_vm_readv,compat_sys_process_vm_readv_wrapper) /* 340 */ -SYSCALL(sys_process_vm_writev,sys_process_vm_writev,compat_sys_process_vm_writev_wrapper) diff --git a/ANDROID_3.4.5/arch/s390/kernel/sysinfo.c b/ANDROID_3.4.5/arch/s390/kernel/sysinfo.c deleted file mode 100644 index 2a94b774..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/sysinfo.c +++ /dev/null @@ -1,470 +0,0 @@ -/* - * Copyright IBM Corp. 2001, 2009 - * Author(s): Ulrich Weigand <Ulrich.Weigand@de.ibm.com>, - * Martin Schwidefsky <schwidefsky@de.ibm.com>, - */ - -#include <linux/kernel.h> -#include <linux/mm.h> -#include <linux/proc_fs.h> -#include <linux/seq_file.h> -#include <linux/init.h> -#include <linux/delay.h> -#include <linux/module.h> -#include <linux/slab.h> -#include <asm/ebcdic.h> -#include <asm/sysinfo.h> -#include <asm/cpcmd.h> -#include <asm/topology.h> - -/* Sigh, math-emu. Don't ask. */ -#include <asm/sfp-util.h> -#include <math-emu/soft-fp.h> -#include <math-emu/single.h> - -static inline int stsi_0(void) -{ - int rc = stsi(NULL, 0, 0, 0); - return rc == -ENOSYS ? rc : (((unsigned int) rc) >> 28); -} - -static int stsi_1_1_1(struct sysinfo_1_1_1 *info, char *page, int len) -{ - if (stsi(info, 1, 1, 1) == -ENOSYS) - return len; - - EBCASC(info->manufacturer, sizeof(info->manufacturer)); - EBCASC(info->type, sizeof(info->type)); - EBCASC(info->model, sizeof(info->model)); - EBCASC(info->sequence, sizeof(info->sequence)); - EBCASC(info->plant, sizeof(info->plant)); - EBCASC(info->model_capacity, sizeof(info->model_capacity)); - EBCASC(info->model_perm_cap, sizeof(info->model_perm_cap)); - EBCASC(info->model_temp_cap, sizeof(info->model_temp_cap)); - len += sprintf(page + len, "Manufacturer: %-16.16s\n", - info->manufacturer); - len += sprintf(page + len, "Type: %-4.4s\n", - info->type); - if (info->model[0] != '\0') - /* - * Sigh: the model field has been renamed with System z9 - * to model_capacity and a new model field has been added - * after the plant field. To avoid confusing older programs - * the "Model:" prints "model_capacity model" or just - * "model_capacity" if the model string is empty . - */ - len += sprintf(page + len, - "Model: %-16.16s %-16.16s\n", - info->model_capacity, info->model); - else - len += sprintf(page + len, "Model: %-16.16s\n", - info->model_capacity); - len += sprintf(page + len, "Sequence Code: %-16.16s\n", - info->sequence); - len += sprintf(page + len, "Plant: %-4.4s\n", - info->plant); - len += sprintf(page + len, "Model Capacity: %-16.16s %08u\n", - info->model_capacity, *(u32 *) info->model_cap_rating); - if (info->model_perm_cap[0] != '\0') - len += sprintf(page + len, - "Model Perm. Capacity: %-16.16s %08u\n", - info->model_perm_cap, - *(u32 *) info->model_perm_cap_rating); - if (info->model_temp_cap[0] != '\0') - len += sprintf(page + len, - "Model Temp. Capacity: %-16.16s %08u\n", - info->model_temp_cap, - *(u32 *) info->model_temp_cap_rating); - if (info->cai) { - len += sprintf(page + len, - "Capacity Adj. Ind.: %d\n", - info->cai); - len += sprintf(page + len, "Capacity Ch. Reason: %d\n", - info->ccr); - } - return len; -} - -static int stsi_15_1_x(struct sysinfo_15_1_x *info, char *page, int len) -{ - static int max_mnest; - int i, rc; - - len += sprintf(page + len, "\n"); - if (!MACHINE_HAS_TOPOLOGY) - return len; - if (max_mnest) { - stsi(info, 15, 1, max_mnest); - } else { - for (max_mnest = 6; max_mnest > 1; max_mnest--) { - rc = stsi(info, 15, 1, max_mnest); - if (rc != -ENOSYS) - break; - } - } - len += sprintf(page + len, "CPU Topology HW: "); - for (i = 0; i < TOPOLOGY_NR_MAG; i++) - len += sprintf(page + len, " %d", info->mag[i]); - len += sprintf(page + len, "\n"); -#ifdef CONFIG_SCHED_MC - store_topology(info); - len += sprintf(page + len, "CPU Topology SW: "); - for (i = 0; i < TOPOLOGY_NR_MAG; i++) - len += sprintf(page + len, " %d", info->mag[i]); - len += sprintf(page + len, "\n"); -#endif - return len; -} - -static int stsi_1_2_2(struct sysinfo_1_2_2 *info, char *page, int len) -{ - struct sysinfo_1_2_2_extension *ext; - int i; - - if (stsi(info, 1, 2, 2) == -ENOSYS) - return len; - ext = (struct sysinfo_1_2_2_extension *) - ((unsigned long) info + info->acc_offset); - - len += sprintf(page + len, "CPUs Total: %d\n", - info->cpus_total); - len += sprintf(page + len, "CPUs Configured: %d\n", - info->cpus_configured); - len += sprintf(page + len, "CPUs Standby: %d\n", - info->cpus_standby); - len += sprintf(page + len, "CPUs Reserved: %d\n", - info->cpus_reserved); - - if (info->format == 1) { - /* - * Sigh 2. According to the specification the alternate - * capability field is a 32 bit floating point number - * if the higher order 8 bits are not zero. Printing - * a floating point number in the kernel is a no-no, - * always print the number as 32 bit unsigned integer. - * The user-space needs to know about the strange - * encoding of the alternate cpu capability. - */ - len += sprintf(page + len, "Capability: %u %u\n", - info->capability, ext->alt_capability); - for (i = 2; i <= info->cpus_total; i++) - len += sprintf(page + len, - "Adjustment %02d-way: %u %u\n", - i, info->adjustment[i-2], - ext->alt_adjustment[i-2]); - - } else { - len += sprintf(page + len, "Capability: %u\n", - info->capability); - for (i = 2; i <= info->cpus_total; i++) - len += sprintf(page + len, - "Adjustment %02d-way: %u\n", - i, info->adjustment[i-2]); - } - - if (info->secondary_capability != 0) - len += sprintf(page + len, "Secondary Capability: %d\n", - info->secondary_capability); - return len; -} - -static int stsi_2_2_2(struct sysinfo_2_2_2 *info, char *page, int len) -{ - if (stsi(info, 2, 2, 2) == -ENOSYS) - return len; - - EBCASC(info->name, sizeof(info->name)); - - len += sprintf(page + len, "\n"); - len += sprintf(page + len, "LPAR Number: %d\n", - info->lpar_number); - - len += sprintf(page + len, "LPAR Characteristics: "); - if (info->characteristics & LPAR_CHAR_DEDICATED) - len += sprintf(page + len, "Dedicated "); - if (info->characteristics & LPAR_CHAR_SHARED) - len += sprintf(page + len, "Shared "); - if (info->characteristics & LPAR_CHAR_LIMITED) - len += sprintf(page + len, "Limited "); - len += sprintf(page + len, "\n"); - - len += sprintf(page + len, "LPAR Name: %-8.8s\n", - info->name); - - len += sprintf(page + len, "LPAR Adjustment: %d\n", - info->caf); - - len += sprintf(page + len, "LPAR CPUs Total: %d\n", - info->cpus_total); - len += sprintf(page + len, "LPAR CPUs Configured: %d\n", - info->cpus_configured); - len += sprintf(page + len, "LPAR CPUs Standby: %d\n", - info->cpus_standby); - len += sprintf(page + len, "LPAR CPUs Reserved: %d\n", - info->cpus_reserved); - len += sprintf(page + len, "LPAR CPUs Dedicated: %d\n", - info->cpus_dedicated); - len += sprintf(page + len, "LPAR CPUs Shared: %d\n", - info->cpus_shared); - return len; -} - -static int stsi_3_2_2(struct sysinfo_3_2_2 *info, char *page, int len) -{ - int i; - - if (stsi(info, 3, 2, 2) == -ENOSYS) - return len; - for (i = 0; i < info->count; i++) { - EBCASC(info->vm[i].name, sizeof(info->vm[i].name)); - EBCASC(info->vm[i].cpi, sizeof(info->vm[i].cpi)); - len += sprintf(page + len, "\n"); - len += sprintf(page + len, "VM%02d Name: %-8.8s\n", - i, info->vm[i].name); - len += sprintf(page + len, "VM%02d Control Program: %-16.16s\n", - i, info->vm[i].cpi); - - len += sprintf(page + len, "VM%02d Adjustment: %d\n", - i, info->vm[i].caf); - - len += sprintf(page + len, "VM%02d CPUs Total: %d\n", - i, info->vm[i].cpus_total); - len += sprintf(page + len, "VM%02d CPUs Configured: %d\n", - i, info->vm[i].cpus_configured); - len += sprintf(page + len, "VM%02d CPUs Standby: %d\n", - i, info->vm[i].cpus_standby); - len += sprintf(page + len, "VM%02d CPUs Reserved: %d\n", - i, info->vm[i].cpus_reserved); - } - return len; -} - -static int proc_read_sysinfo(char *page, char **start, - off_t off, int count, - int *eof, void *data) -{ - unsigned long info = get_zeroed_page(GFP_KERNEL); - int level, len; - - if (!info) - return 0; - - len = 0; - level = stsi_0(); - if (level >= 1) - len = stsi_1_1_1((struct sysinfo_1_1_1 *) info, page, len); - - if (level >= 1) - len = stsi_15_1_x((struct sysinfo_15_1_x *) info, page, len); - - if (level >= 1) - len = stsi_1_2_2((struct sysinfo_1_2_2 *) info, page, len); - - if (level >= 2) - len = stsi_2_2_2((struct sysinfo_2_2_2 *) info, page, len); - - if (level >= 3) - len = stsi_3_2_2((struct sysinfo_3_2_2 *) info, page, len); - - free_page(info); - return len; -} - -static __init int create_proc_sysinfo(void) -{ - create_proc_read_entry("sysinfo", 0444, NULL, - proc_read_sysinfo, NULL); - return 0; -} -device_initcall(create_proc_sysinfo); - -/* - * Service levels interface. - */ - -static DECLARE_RWSEM(service_level_sem); -static LIST_HEAD(service_level_list); - -int register_service_level(struct service_level *slr) -{ - struct service_level *ptr; - - down_write(&service_level_sem); - list_for_each_entry(ptr, &service_level_list, list) - if (ptr == slr) { - up_write(&service_level_sem); - return -EEXIST; - } - list_add_tail(&slr->list, &service_level_list); - up_write(&service_level_sem); - return 0; -} -EXPORT_SYMBOL(register_service_level); - -int unregister_service_level(struct service_level *slr) -{ - struct service_level *ptr, *next; - int rc = -ENOENT; - - down_write(&service_level_sem); - list_for_each_entry_safe(ptr, next, &service_level_list, list) { - if (ptr != slr) - continue; - list_del(&ptr->list); - rc = 0; - break; - } - up_write(&service_level_sem); - return rc; -} -EXPORT_SYMBOL(unregister_service_level); - -static void *service_level_start(struct seq_file *m, loff_t *pos) -{ - down_read(&service_level_sem); - return seq_list_start(&service_level_list, *pos); -} - -static void *service_level_next(struct seq_file *m, void *p, loff_t *pos) -{ - return seq_list_next(p, &service_level_list, pos); -} - -static void service_level_stop(struct seq_file *m, void *p) -{ - up_read(&service_level_sem); -} - -static int service_level_show(struct seq_file *m, void *p) -{ - struct service_level *slr; - - slr = list_entry(p, struct service_level, list); - slr->seq_print(m, slr); - return 0; -} - -static const struct seq_operations service_level_seq_ops = { - .start = service_level_start, - .next = service_level_next, - .stop = service_level_stop, - .show = service_level_show -}; - -static int service_level_open(struct inode *inode, struct file *file) -{ - return seq_open(file, &service_level_seq_ops); -} - -static const struct file_operations service_level_ops = { - .open = service_level_open, - .read = seq_read, - .llseek = seq_lseek, - .release = seq_release -}; - -static void service_level_vm_print(struct seq_file *m, - struct service_level *slr) -{ - char *query_buffer, *str; - - query_buffer = kmalloc(1024, GFP_KERNEL | GFP_DMA); - if (!query_buffer) - return; - cpcmd("QUERY CPLEVEL", query_buffer, 1024, NULL); - str = strchr(query_buffer, '\n'); - if (str) - *str = 0; - seq_printf(m, "VM: %s\n", query_buffer); - kfree(query_buffer); -} - -static struct service_level service_level_vm = { - .seq_print = service_level_vm_print -}; - -static __init int create_proc_service_level(void) -{ - proc_create("service_levels", 0, NULL, &service_level_ops); - if (MACHINE_IS_VM) - register_service_level(&service_level_vm); - return 0; -} -subsys_initcall(create_proc_service_level); - -/* - * Bogomips calculation based on cpu capability. - */ -int get_cpu_capability(unsigned int *capability) -{ - struct sysinfo_1_2_2 *info; - int rc; - - info = (void *) get_zeroed_page(GFP_KERNEL); - if (!info) - return -ENOMEM; - rc = stsi(info, 1, 2, 2); - if (rc == -ENOSYS) - goto out; - rc = 0; - *capability = info->capability; -out: - free_page((unsigned long) info); - return rc; -} - -/* - * CPU capability might have changed. Therefore recalculate loops_per_jiffy. - */ -void s390_adjust_jiffies(void) -{ - struct sysinfo_1_2_2 *info; - const unsigned int fmil = 0x4b189680; /* 1e7 as 32-bit float. */ - FP_DECL_S(SA); FP_DECL_S(SB); FP_DECL_S(SR); - FP_DECL_EX; - unsigned int capability; - - info = (void *) get_zeroed_page(GFP_KERNEL); - if (!info) - return; - - if (stsi(info, 1, 2, 2) != -ENOSYS) { - /* - * Major sigh. The cpu capability encoding is "special". - * If the first 9 bits of info->capability are 0 then it - * is a 32 bit unsigned integer in the range 0 .. 2^23. - * If the first 9 bits are != 0 then it is a 32 bit float. - * In addition a lower value indicates a proportionally - * higher cpu capacity. Bogomips are the other way round. - * To get to a halfway suitable number we divide 1e7 - * by the cpu capability number. Yes, that means a floating - * point division .. math-emu here we come :-) - */ - FP_UNPACK_SP(SA, &fmil); - if ((info->capability >> 23) == 0) - FP_FROM_INT_S(SB, (long) info->capability, 64, long); - else - FP_UNPACK_SP(SB, &info->capability); - FP_DIV_S(SR, SA, SB); - FP_TO_INT_S(capability, SR, 32, 0); - } else - /* - * Really old machine without stsi block for basic - * cpu information. Report 42.0 bogomips. - */ - capability = 42; - loops_per_jiffy = capability * (500000/HZ); - free_page((unsigned long) info); -} - -/* - * calibrate the delay loop - */ -void __cpuinit calibrate_delay(void) -{ - s390_adjust_jiffies(); - /* Print the good old Bogomips line .. */ - printk(KERN_DEBUG "Calibrating delay loop (skipped)... " - "%lu.%02lu BogoMIPS preset\n", loops_per_jiffy/(500000/HZ), - (loops_per_jiffy/(5000/HZ)) % 100); -} diff --git a/ANDROID_3.4.5/arch/s390/kernel/time.c b/ANDROID_3.4.5/arch/s390/kernel/time.c deleted file mode 100644 index d4e1cb1d..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/time.c +++ /dev/null @@ -1,1789 +0,0 @@ -/* - * arch/s390/kernel/time.c - * Time of day based timer functions. - * - * S390 version - * Copyright IBM Corp. 1999, 2008 - * Author(s): Hartmut Penner (hp@de.ibm.com), - * Martin Schwidefsky (schwidefsky@de.ibm.com), - * Denis Joseph Barrow (djbarrow@de.ibm.com,barrow_dj@yahoo.com) - * - * Derived from "arch/i386/kernel/time.c" - * Copyright (C) 1991, 1992, 1995 Linus Torvalds - */ - -#define KMSG_COMPONENT "time" -#define pr_fmt(fmt) KMSG_COMPONENT ": " fmt - -#include <linux/kernel_stat.h> -#include <linux/errno.h> -#include <linux/module.h> -#include <linux/sched.h> -#include <linux/kernel.h> -#include <linux/param.h> -#include <linux/string.h> -#include <linux/mm.h> -#include <linux/interrupt.h> -#include <linux/cpu.h> -#include <linux/stop_machine.h> -#include <linux/time.h> -#include <linux/device.h> -#include <linux/delay.h> -#include <linux/init.h> -#include <linux/smp.h> -#include <linux/types.h> -#include <linux/profile.h> -#include <linux/timex.h> -#include <linux/notifier.h> -#include <linux/clocksource.h> -#include <linux/clockchips.h> -#include <linux/gfp.h> -#include <linux/kprobes.h> -#include <asm/uaccess.h> -#include <asm/delay.h> -#include <asm/div64.h> -#include <asm/vdso.h> -#include <asm/irq.h> -#include <asm/irq_regs.h> -#include <asm/timer.h> -#include <asm/etr.h> -#include <asm/cio.h> -#include "entry.h" - -/* change this if you have some constant time drift */ -#define USECS_PER_JIFFY ((unsigned long) 1000000/HZ) -#define CLK_TICKS_PER_JIFFY ((unsigned long) USECS_PER_JIFFY << 12) - -u64 sched_clock_base_cc = -1; /* Force to data section. */ -EXPORT_SYMBOL_GPL(sched_clock_base_cc); - -static DEFINE_PER_CPU(struct clock_event_device, comparators); - -/* - * Scheduler clock - returns current time in nanosec units. - */ -unsigned long long notrace __kprobes sched_clock(void) -{ - return (get_clock_monotonic() * 125) >> 9; -} - -/* - * Monotonic_clock - returns # of nanoseconds passed since time_init() - */ -unsigned long long monotonic_clock(void) -{ - return sched_clock(); -} -EXPORT_SYMBOL(monotonic_clock); - -void tod_to_timeval(__u64 todval, struct timespec *xt) -{ - unsigned long long sec; - - sec = todval >> 12; - do_div(sec, 1000000); - xt->tv_sec = sec; - todval -= (sec * 1000000) << 12; - xt->tv_nsec = ((todval * 1000) >> 12); -} -EXPORT_SYMBOL(tod_to_timeval); - -void clock_comparator_work(void) -{ - struct clock_event_device *cd; - - S390_lowcore.clock_comparator = -1ULL; - set_clock_comparator(S390_lowcore.clock_comparator); - cd = &__get_cpu_var(comparators); - cd->event_handler(cd); -} - -/* - * Fixup the clock comparator. - */ -static void fixup_clock_comparator(unsigned long long delta) -{ - /* If nobody is waiting there's nothing to fix. */ - if (S390_lowcore.clock_comparator == -1ULL) - return; - S390_lowcore.clock_comparator += delta; - set_clock_comparator(S390_lowcore.clock_comparator); -} - -static int s390_next_ktime(ktime_t expires, - struct clock_event_device *evt) -{ - struct timespec ts; - u64 nsecs; - - ts.tv_sec = ts.tv_nsec = 0; - monotonic_to_bootbased(&ts); - nsecs = ktime_to_ns(ktime_add(timespec_to_ktime(ts), expires)); - do_div(nsecs, 125); - S390_lowcore.clock_comparator = sched_clock_base_cc + (nsecs << 9); - set_clock_comparator(S390_lowcore.clock_comparator); - return 0; -} - -static void s390_set_mode(enum clock_event_mode mode, - struct clock_event_device *evt) -{ -} - -/* - * Set up lowcore and control register of the current cpu to - * enable TOD clock and clock comparator interrupts. - */ -void init_cpu_timer(void) -{ - struct clock_event_device *cd; - int cpu; - - S390_lowcore.clock_comparator = -1ULL; - set_clock_comparator(S390_lowcore.clock_comparator); - - cpu = smp_processor_id(); - cd = &per_cpu(comparators, cpu); - cd->name = "comparator"; - cd->features = CLOCK_EVT_FEAT_ONESHOT | - CLOCK_EVT_FEAT_KTIME; - cd->mult = 16777; - cd->shift = 12; - cd->min_delta_ns = 1; - cd->max_delta_ns = LONG_MAX; - cd->rating = 400; - cd->cpumask = cpumask_of(cpu); - cd->set_next_ktime = s390_next_ktime; - cd->set_mode = s390_set_mode; - - clockevents_register_device(cd); - - /* Enable clock comparator timer interrupt. */ - __ctl_set_bit(0,11); - - /* Always allow the timing alert external interrupt. */ - __ctl_set_bit(0, 4); -} - -static void clock_comparator_interrupt(struct ext_code ext_code, - unsigned int param32, - unsigned long param64) -{ - kstat_cpu(smp_processor_id()).irqs[EXTINT_CLK]++; - if (S390_lowcore.clock_comparator == -1ULL) - set_clock_comparator(S390_lowcore.clock_comparator); -} - -static void etr_timing_alert(struct etr_irq_parm *); -static void stp_timing_alert(struct stp_irq_parm *); - -static void timing_alert_interrupt(struct ext_code ext_code, - unsigned int param32, unsigned long param64) -{ - kstat_cpu(smp_processor_id()).irqs[EXTINT_TLA]++; - if (param32 & 0x00c40000) - etr_timing_alert((struct etr_irq_parm *) ¶m32); - if (param32 & 0x00038000) - stp_timing_alert((struct stp_irq_parm *) ¶m32); -} - -static void etr_reset(void); -static void stp_reset(void); - -void read_persistent_clock(struct timespec *ts) -{ - tod_to_timeval(get_clock() - TOD_UNIX_EPOCH, ts); -} - -void read_boot_clock(struct timespec *ts) -{ - tod_to_timeval(sched_clock_base_cc - TOD_UNIX_EPOCH, ts); -} - -static cycle_t read_tod_clock(struct clocksource *cs) -{ - return get_clock(); -} - -static struct clocksource clocksource_tod = { - .name = "tod", - .rating = 400, - .read = read_tod_clock, - .mask = -1ULL, - .mult = 1000, - .shift = 12, - .flags = CLOCK_SOURCE_IS_CONTINUOUS, -}; - -struct clocksource * __init clocksource_default_clock(void) -{ - return &clocksource_tod; -} - -void update_vsyscall(struct timespec *wall_time, struct timespec *wtm, - struct clocksource *clock, u32 mult) -{ - if (clock != &clocksource_tod) - return; - - /* Make userspace gettimeofday spin until we're done. */ - ++vdso_data->tb_update_count; - smp_wmb(); - vdso_data->xtime_tod_stamp = clock->cycle_last; - vdso_data->xtime_clock_sec = wall_time->tv_sec; - vdso_data->xtime_clock_nsec = wall_time->tv_nsec; - vdso_data->wtom_clock_sec = wtm->tv_sec; - vdso_data->wtom_clock_nsec = wtm->tv_nsec; - vdso_data->ntp_mult = mult; - smp_wmb(); - ++vdso_data->tb_update_count; -} - -extern struct timezone sys_tz; - -void update_vsyscall_tz(void) -{ - /* Make userspace gettimeofday spin until we're done. */ - ++vdso_data->tb_update_count; - smp_wmb(); - vdso_data->tz_minuteswest = sys_tz.tz_minuteswest; - vdso_data->tz_dsttime = sys_tz.tz_dsttime; - smp_wmb(); - ++vdso_data->tb_update_count; -} - -/* - * Initialize the TOD clock and the CPU timer of - * the boot cpu. - */ -void __init time_init(void) -{ - /* Reset time synchronization interfaces. */ - etr_reset(); - stp_reset(); - - /* request the clock comparator external interrupt */ - if (register_external_interrupt(0x1004, clock_comparator_interrupt)) - panic("Couldn't request external interrupt 0x1004"); - - /* request the timing alert external interrupt */ - if (register_external_interrupt(0x1406, timing_alert_interrupt)) - panic("Couldn't request external interrupt 0x1406"); - - if (clocksource_register(&clocksource_tod) != 0) - panic("Could not register TOD clock source"); - - /* Enable TOD clock interrupts on the boot cpu. */ - init_cpu_timer(); - - /* Enable cpu timer interrupts on the boot cpu. */ - vtime_init(); -} - -/* - * The time is "clock". old is what we think the time is. - * Adjust the value by a multiple of jiffies and add the delta to ntp. - * "delay" is an approximation how long the synchronization took. If - * the time correction is positive, then "delay" is subtracted from - * the time difference and only the remaining part is passed to ntp. - */ -static unsigned long long adjust_time(unsigned long long old, - unsigned long long clock, - unsigned long long delay) -{ - unsigned long long delta, ticks; - struct timex adjust; - - if (clock > old) { - /* It is later than we thought. */ - delta = ticks = clock - old; - delta = ticks = (delta < delay) ? 0 : delta - delay; - delta -= do_div(ticks, CLK_TICKS_PER_JIFFY); - adjust.offset = ticks * (1000000 / HZ); - } else { - /* It is earlier than we thought. */ - delta = ticks = old - clock; - delta -= do_div(ticks, CLK_TICKS_PER_JIFFY); - delta = -delta; - adjust.offset = -ticks * (1000000 / HZ); - } - sched_clock_base_cc += delta; - if (adjust.offset != 0) { - pr_notice("The ETR interface has adjusted the clock " - "by %li microseconds\n", adjust.offset); - adjust.modes = ADJ_OFFSET_SINGLESHOT; - do_adjtimex(&adjust); - } - return delta; -} - -static DEFINE_PER_CPU(atomic_t, clock_sync_word); -static DEFINE_MUTEX(clock_sync_mutex); -static unsigned long clock_sync_flags; - -#define CLOCK_SYNC_HAS_ETR 0 -#define CLOCK_SYNC_HAS_STP 1 -#define CLOCK_SYNC_ETR 2 -#define CLOCK_SYNC_STP 3 - -/* - * The synchronous get_clock function. It will write the current clock - * value to the clock pointer and return 0 if the clock is in sync with - * the external time source. If the clock mode is local it will return - * -ENOSYS and -EAGAIN if the clock is not in sync with the external - * reference. - */ -int get_sync_clock(unsigned long long *clock) -{ - atomic_t *sw_ptr; - unsigned int sw0, sw1; - - sw_ptr = &get_cpu_var(clock_sync_word); - sw0 = atomic_read(sw_ptr); - *clock = get_clock(); - sw1 = atomic_read(sw_ptr); - put_cpu_var(clock_sync_word); - if (sw0 == sw1 && (sw0 & 0x80000000U)) - /* Success: time is in sync. */ - return 0; - if (!test_bit(CLOCK_SYNC_HAS_ETR, &clock_sync_flags) && - !test_bit(CLOCK_SYNC_HAS_STP, &clock_sync_flags)) - return -ENOSYS; - if (!test_bit(CLOCK_SYNC_ETR, &clock_sync_flags) && - !test_bit(CLOCK_SYNC_STP, &clock_sync_flags)) - return -EACCES; - return -EAGAIN; -} -EXPORT_SYMBOL(get_sync_clock); - -/* - * Make get_sync_clock return -EAGAIN. - */ -static void disable_sync_clock(void *dummy) -{ - atomic_t *sw_ptr = &__get_cpu_var(clock_sync_word); - /* - * Clear the in-sync bit 2^31. All get_sync_clock calls will - * fail until the sync bit is turned back on. In addition - * increase the "sequence" counter to avoid the race of an - * etr event and the complete recovery against get_sync_clock. - */ - atomic_clear_mask(0x80000000, sw_ptr); - atomic_inc(sw_ptr); -} - -/* - * Make get_sync_clock return 0 again. - * Needs to be called from a context disabled for preemption. - */ -static void enable_sync_clock(void) -{ - atomic_t *sw_ptr = &__get_cpu_var(clock_sync_word); - atomic_set_mask(0x80000000, sw_ptr); -} - -/* - * Function to check if the clock is in sync. - */ -static inline int check_sync_clock(void) -{ - atomic_t *sw_ptr; - int rc; - - sw_ptr = &get_cpu_var(clock_sync_word); - rc = (atomic_read(sw_ptr) & 0x80000000U) != 0; - put_cpu_var(clock_sync_word); - return rc; -} - -/* Single threaded workqueue used for etr and stp sync events */ -static struct workqueue_struct *time_sync_wq; - -static void __init time_init_wq(void) -{ - if (time_sync_wq) - return; - time_sync_wq = create_singlethread_workqueue("timesync"); -} - -/* - * External Time Reference (ETR) code. - */ -static int etr_port0_online; -static int etr_port1_online; -static int etr_steai_available; - -static int __init early_parse_etr(char *p) -{ - if (strncmp(p, "off", 3) == 0) - etr_port0_online = etr_port1_online = 0; - else if (strncmp(p, "port0", 5) == 0) - etr_port0_online = 1; - else if (strncmp(p, "port1", 5) == 0) - etr_port1_online = 1; - else if (strncmp(p, "on", 2) == 0) - etr_port0_online = etr_port1_online = 1; - return 0; -} -early_param("etr", early_parse_etr); - -enum etr_event { - ETR_EVENT_PORT0_CHANGE, - ETR_EVENT_PORT1_CHANGE, - ETR_EVENT_PORT_ALERT, - ETR_EVENT_SYNC_CHECK, - ETR_EVENT_SWITCH_LOCAL, - ETR_EVENT_UPDATE, -}; - -/* - * Valid bit combinations of the eacr register are (x = don't care): - * e0 e1 dp p0 p1 ea es sl - * 0 0 x 0 0 0 0 0 initial, disabled state - * 0 0 x 0 1 1 0 0 port 1 online - * 0 0 x 1 0 1 0 0 port 0 online - * 0 0 x 1 1 1 0 0 both ports online - * 0 1 x 0 1 1 0 0 port 1 online and usable, ETR or PPS mode - * 0 1 x 0 1 1 0 1 port 1 online, usable and ETR mode - * 0 1 x 0 1 1 1 0 port 1 online, usable, PPS mode, in-sync - * 0 1 x 0 1 1 1 1 port 1 online, usable, ETR mode, in-sync - * 0 1 x 1 1 1 0 0 both ports online, port 1 usable - * 0 1 x 1 1 1 1 0 both ports online, port 1 usable, PPS mode, in-sync - * 0 1 x 1 1 1 1 1 both ports online, port 1 usable, ETR mode, in-sync - * 1 0 x 1 0 1 0 0 port 0 online and usable, ETR or PPS mode - * 1 0 x 1 0 1 0 1 port 0 online, usable and ETR mode - * 1 0 x 1 0 1 1 0 port 0 online, usable, PPS mode, in-sync - * 1 0 x 1 0 1 1 1 port 0 online, usable, ETR mode, in-sync - * 1 0 x 1 1 1 0 0 both ports online, port 0 usable - * 1 0 x 1 1 1 1 0 both ports online, port 0 usable, PPS mode, in-sync - * 1 0 x 1 1 1 1 1 both ports online, port 0 usable, ETR mode, in-sync - * 1 1 x 1 1 1 1 0 both ports online & usable, ETR, in-sync - * 1 1 x 1 1 1 1 1 both ports online & usable, ETR, in-sync - */ -static struct etr_eacr etr_eacr; -static u64 etr_tolec; /* time of last eacr update */ -static struct etr_aib etr_port0; -static int etr_port0_uptodate; -static struct etr_aib etr_port1; -static int etr_port1_uptodate; -static unsigned long etr_events; -static struct timer_list etr_timer; - -static void etr_timeout(unsigned long dummy); -static void etr_work_fn(struct work_struct *work); -static DEFINE_MUTEX(etr_work_mutex); -static DECLARE_WORK(etr_work, etr_work_fn); - -/* - * Reset ETR attachment. - */ -static void etr_reset(void) -{ - etr_eacr = (struct etr_eacr) { - .e0 = 0, .e1 = 0, ._pad0 = 4, .dp = 0, - .p0 = 0, .p1 = 0, ._pad1 = 0, .ea = 0, - .es = 0, .sl = 0 }; - if (etr_setr(&etr_eacr) == 0) { - etr_tolec = get_clock(); - set_bit(CLOCK_SYNC_HAS_ETR, &clock_sync_flags); - if (etr_port0_online && etr_port1_online) - set_bit(CLOCK_SYNC_ETR, &clock_sync_flags); - } else if (etr_port0_online || etr_port1_online) { - pr_warning("The real or virtual hardware system does " - "not provide an ETR interface\n"); - etr_port0_online = etr_port1_online = 0; - } -} - -static int __init etr_init(void) -{ - struct etr_aib aib; - - if (!test_bit(CLOCK_SYNC_HAS_ETR, &clock_sync_flags)) - return 0; - time_init_wq(); - /* Check if this machine has the steai instruction. */ - if (etr_steai(&aib, ETR_STEAI_STEPPING_PORT) == 0) - etr_steai_available = 1; - setup_timer(&etr_timer, etr_timeout, 0UL); - if (etr_port0_online) { - set_bit(ETR_EVENT_PORT0_CHANGE, &etr_events); - queue_work(time_sync_wq, &etr_work); - } - if (etr_port1_online) { - set_bit(ETR_EVENT_PORT1_CHANGE, &etr_events); - queue_work(time_sync_wq, &etr_work); - } - return 0; -} - -arch_initcall(etr_init); - -/* - * Two sorts of ETR machine checks. The architecture reads: - * "When a machine-check niterruption occurs and if a switch-to-local or - * ETR-sync-check interrupt request is pending but disabled, this pending - * disabled interruption request is indicated and is cleared". - * Which means that we can get etr_switch_to_local events from the machine - * check handler although the interruption condition is disabled. Lovely.. - */ - -/* - * Switch to local machine check. This is called when the last usable - * ETR port goes inactive. After switch to local the clock is not in sync. - */ -void etr_switch_to_local(void) -{ - if (!etr_eacr.sl) - return; - disable_sync_clock(NULL); - if (!test_and_set_bit(ETR_EVENT_SWITCH_LOCAL, &etr_events)) { - etr_eacr.es = etr_eacr.sl = 0; - etr_setr(&etr_eacr); - queue_work(time_sync_wq, &etr_work); - } -} - -/* - * ETR sync check machine check. This is called when the ETR OTE and the - * local clock OTE are farther apart than the ETR sync check tolerance. - * After a ETR sync check the clock is not in sync. The machine check - * is broadcasted to all cpus at the same time. - */ -void etr_sync_check(void) -{ - if (!etr_eacr.es) - return; - disable_sync_clock(NULL); - if (!test_and_set_bit(ETR_EVENT_SYNC_CHECK, &etr_events)) { - etr_eacr.es = 0; - etr_setr(&etr_eacr); - queue_work(time_sync_wq, &etr_work); - } -} - -/* - * ETR timing alert. There are two causes: - * 1) port state change, check the usability of the port - * 2) port alert, one of the ETR-data-validity bits (v1-v2 bits of the - * sldr-status word) or ETR-data word 1 (edf1) or ETR-data word 3 (edf3) - * or ETR-data word 4 (edf4) has changed. - */ -static void etr_timing_alert(struct etr_irq_parm *intparm) -{ - if (intparm->pc0) - /* ETR port 0 state change. */ - set_bit(ETR_EVENT_PORT0_CHANGE, &etr_events); - if (intparm->pc1) - /* ETR port 1 state change. */ - set_bit(ETR_EVENT_PORT1_CHANGE, &etr_events); - if (intparm->eai) - /* - * ETR port alert on either port 0, 1 or both. - * Both ports are not up-to-date now. - */ - set_bit(ETR_EVENT_PORT_ALERT, &etr_events); - queue_work(time_sync_wq, &etr_work); -} - -static void etr_timeout(unsigned long dummy) -{ - set_bit(ETR_EVENT_UPDATE, &etr_events); - queue_work(time_sync_wq, &etr_work); -} - -/* - * Check if the etr mode is pss. - */ -static inline int etr_mode_is_pps(struct etr_eacr eacr) -{ - return eacr.es && !eacr.sl; -} - -/* - * Check if the etr mode is etr. - */ -static inline int etr_mode_is_etr(struct etr_eacr eacr) -{ - return eacr.es && eacr.sl; -} - -/* - * Check if the port can be used for TOD synchronization. - * For PPS mode the port has to receive OTEs. For ETR mode - * the port has to receive OTEs, the ETR stepping bit has to - * be zero and the validity bits for data frame 1, 2, and 3 - * have to be 1. - */ -static int etr_port_valid(struct etr_aib *aib, int port) -{ - unsigned int psc; - - /* Check that this port is receiving OTEs. */ - if (aib->tsp == 0) - return 0; - - psc = port ? aib->esw.psc1 : aib->esw.psc0; - if (psc == etr_lpsc_pps_mode) - return 1; - if (psc == etr_lpsc_operational_step) - return !aib->esw.y && aib->slsw.v1 && - aib->slsw.v2 && aib->slsw.v3; - return 0; -} - -/* - * Check if two ports are on the same network. - */ -static int etr_compare_network(struct etr_aib *aib1, struct etr_aib *aib2) -{ - // FIXME: any other fields we have to compare? - return aib1->edf1.net_id == aib2->edf1.net_id; -} - -/* - * Wrapper for etr_stei that converts physical port states - * to logical port states to be consistent with the output - * of stetr (see etr_psc vs. etr_lpsc). - */ -static void etr_steai_cv(struct etr_aib *aib, unsigned int func) -{ - BUG_ON(etr_steai(aib, func) != 0); - /* Convert port state to logical port state. */ - if (aib->esw.psc0 == 1) - aib->esw.psc0 = 2; - else if (aib->esw.psc0 == 0 && aib->esw.p == 0) - aib->esw.psc0 = 1; - if (aib->esw.psc1 == 1) - aib->esw.psc1 = 2; - else if (aib->esw.psc1 == 0 && aib->esw.p == 1) - aib->esw.psc1 = 1; -} - -/* - * Check if the aib a2 is still connected to the same attachment as - * aib a1, the etv values differ by one and a2 is valid. - */ -static int etr_aib_follows(struct etr_aib *a1, struct etr_aib *a2, int p) -{ - int state_a1, state_a2; - - /* Paranoia check: e0/e1 should better be the same. */ - if (a1->esw.eacr.e0 != a2->esw.eacr.e0 || - a1->esw.eacr.e1 != a2->esw.eacr.e1) - return 0; - - /* Still connected to the same etr ? */ - state_a1 = p ? a1->esw.psc1 : a1->esw.psc0; - state_a2 = p ? a2->esw.psc1 : a2->esw.psc0; - if (state_a1 == etr_lpsc_operational_step) { - if (state_a2 != etr_lpsc_operational_step || - a1->edf1.net_id != a2->edf1.net_id || - a1->edf1.etr_id != a2->edf1.etr_id || - a1->edf1.etr_pn != a2->edf1.etr_pn) - return 0; - } else if (state_a2 != etr_lpsc_pps_mode) - return 0; - - /* The ETV value of a2 needs to be ETV of a1 + 1. */ - if (a1->edf2.etv + 1 != a2->edf2.etv) - return 0; - - if (!etr_port_valid(a2, p)) - return 0; - - return 1; -} - -struct clock_sync_data { - atomic_t cpus; - int in_sync; - unsigned long long fixup_cc; - int etr_port; - struct etr_aib *etr_aib; -}; - -static void clock_sync_cpu(struct clock_sync_data *sync) -{ - atomic_dec(&sync->cpus); - enable_sync_clock(); - /* - * This looks like a busy wait loop but it isn't. etr_sync_cpus - * is called on all other cpus while the TOD clocks is stopped. - * __udelay will stop the cpu on an enabled wait psw until the - * TOD is running again. - */ - while (sync->in_sync == 0) { - __udelay(1); - /* - * A different cpu changes *in_sync. Therefore use - * barrier() to force memory access. - */ - barrier(); - } - if (sync->in_sync != 1) - /* Didn't work. Clear per-cpu in sync bit again. */ - disable_sync_clock(NULL); - /* - * This round of TOD syncing is done. Set the clock comparator - * to the next tick and let the processor continue. - */ - fixup_clock_comparator(sync->fixup_cc); -} - -/* - * Sync the TOD clock using the port referred to by aibp. This port - * has to be enabled and the other port has to be disabled. The - * last eacr update has to be more than 1.6 seconds in the past. - */ -static int etr_sync_clock(void *data) -{ - static int first; - unsigned long long clock, old_clock, delay, delta; - struct clock_sync_data *etr_sync; - struct etr_aib *sync_port, *aib; - int port; - int rc; - - etr_sync = data; - - if (xchg(&first, 1) == 1) { - /* Slave */ - clock_sync_cpu(etr_sync); - return 0; - } - - /* Wait until all other cpus entered the sync function. */ - while (atomic_read(&etr_sync->cpus) != 0) - cpu_relax(); - - port = etr_sync->etr_port; - aib = etr_sync->etr_aib; - sync_port = (port == 0) ? &etr_port0 : &etr_port1; - enable_sync_clock(); - - /* Set clock to next OTE. */ - __ctl_set_bit(14, 21); - __ctl_set_bit(0, 29); - clock = ((unsigned long long) (aib->edf2.etv + 1)) << 32; - old_clock = get_clock(); - if (set_clock(clock) == 0) { - __udelay(1); /* Wait for the clock to start. */ - __ctl_clear_bit(0, 29); - __ctl_clear_bit(14, 21); - etr_stetr(aib); - /* Adjust Linux timing variables. */ - delay = (unsigned long long) - (aib->edf2.etv - sync_port->edf2.etv) << 32; - delta = adjust_time(old_clock, clock, delay); - etr_sync->fixup_cc = delta; - fixup_clock_comparator(delta); - /* Verify that the clock is properly set. */ - if (!etr_aib_follows(sync_port, aib, port)) { - /* Didn't work. */ - disable_sync_clock(NULL); - etr_sync->in_sync = -EAGAIN; - rc = -EAGAIN; - } else { - etr_sync->in_sync = 1; - rc = 0; - } - } else { - /* Could not set the clock ?!? */ - __ctl_clear_bit(0, 29); - __ctl_clear_bit(14, 21); - disable_sync_clock(NULL); - etr_sync->in_sync = -EAGAIN; - rc = -EAGAIN; - } - xchg(&first, 0); - return rc; -} - -static int etr_sync_clock_stop(struct etr_aib *aib, int port) -{ - struct clock_sync_data etr_sync; - struct etr_aib *sync_port; - int follows; - int rc; - - /* Check if the current aib is adjacent to the sync port aib. */ - sync_port = (port == 0) ? &etr_port0 : &etr_port1; - follows = etr_aib_follows(sync_port, aib, port); - memcpy(sync_port, aib, sizeof(*aib)); - if (!follows) - return -EAGAIN; - memset(&etr_sync, 0, sizeof(etr_sync)); - etr_sync.etr_aib = aib; - etr_sync.etr_port = port; - get_online_cpus(); - atomic_set(&etr_sync.cpus, num_online_cpus() - 1); - rc = stop_machine(etr_sync_clock, &etr_sync, cpu_online_mask); - put_online_cpus(); - return rc; -} - -/* - * Handle the immediate effects of the different events. - * The port change event is used for online/offline changes. - */ -static struct etr_eacr etr_handle_events(struct etr_eacr eacr) -{ - if (test_and_clear_bit(ETR_EVENT_SYNC_CHECK, &etr_events)) - eacr.es = 0; - if (test_and_clear_bit(ETR_EVENT_SWITCH_LOCAL, &etr_events)) - eacr.es = eacr.sl = 0; - if (test_and_clear_bit(ETR_EVENT_PORT_ALERT, &etr_events)) - etr_port0_uptodate = etr_port1_uptodate = 0; - - if (test_and_clear_bit(ETR_EVENT_PORT0_CHANGE, &etr_events)) { - if (eacr.e0) - /* - * Port change of an enabled port. We have to - * assume that this can have caused an stepping - * port switch. - */ - etr_tolec = get_clock(); - eacr.p0 = etr_port0_online; - if (!eacr.p0) - eacr.e0 = 0; - etr_port0_uptodate = 0; - } - if (test_and_clear_bit(ETR_EVENT_PORT1_CHANGE, &etr_events)) { - if (eacr.e1) - /* - * Port change of an enabled port. We have to - * assume that this can have caused an stepping - * port switch. - */ - etr_tolec = get_clock(); - eacr.p1 = etr_port1_online; - if (!eacr.p1) - eacr.e1 = 0; - etr_port1_uptodate = 0; - } - clear_bit(ETR_EVENT_UPDATE, &etr_events); - return eacr; -} - -/* - * Set up a timer that expires after the etr_tolec + 1.6 seconds if - * one of the ports needs an update. - */ -static void etr_set_tolec_timeout(unsigned long long now) -{ - unsigned long micros; - - if ((!etr_eacr.p0 || etr_port0_uptodate) && - (!etr_eacr.p1 || etr_port1_uptodate)) - return; - micros = (now > etr_tolec) ? ((now - etr_tolec) >> 12) : 0; - micros = (micros > 1600000) ? 0 : 1600000 - micros; - mod_timer(&etr_timer, jiffies + (micros * HZ) / 1000000 + 1); -} - -/* - * Set up a time that expires after 1/2 second. - */ -static void etr_set_sync_timeout(void) -{ - mod_timer(&etr_timer, jiffies + HZ/2); -} - -/* - * Update the aib information for one or both ports. - */ -static struct etr_eacr etr_handle_update(struct etr_aib *aib, - struct etr_eacr eacr) -{ - /* With both ports disabled the aib information is useless. */ - if (!eacr.e0 && !eacr.e1) - return eacr; - - /* Update port0 or port1 with aib stored in etr_work_fn. */ - if (aib->esw.q == 0) { - /* Information for port 0 stored. */ - if (eacr.p0 && !etr_port0_uptodate) { - etr_port0 = *aib; - if (etr_port0_online) - etr_port0_uptodate = 1; - } - } else { - /* Information for port 1 stored. */ - if (eacr.p1 && !etr_port1_uptodate) { - etr_port1 = *aib; - if (etr_port0_online) - etr_port1_uptodate = 1; - } - } - - /* - * Do not try to get the alternate port aib if the clock - * is not in sync yet. - */ - if (!eacr.es || !check_sync_clock()) - return eacr; - - /* - * If steai is available we can get the information about - * the other port immediately. If only stetr is available the - * data-port bit toggle has to be used. - */ - if (etr_steai_available) { - if (eacr.p0 && !etr_port0_uptodate) { - etr_steai_cv(&etr_port0, ETR_STEAI_PORT_0); - etr_port0_uptodate = 1; - } - if (eacr.p1 && !etr_port1_uptodate) { - etr_steai_cv(&etr_port1, ETR_STEAI_PORT_1); - etr_port1_uptodate = 1; - } - } else { - /* - * One port was updated above, if the other - * port is not uptodate toggle dp bit. - */ - if ((eacr.p0 && !etr_port0_uptodate) || - (eacr.p1 && !etr_port1_uptodate)) - eacr.dp ^= 1; - else - eacr.dp = 0; - } - return eacr; -} - -/* - * Write new etr control register if it differs from the current one. - * Return 1 if etr_tolec has been updated as well. - */ -static void etr_update_eacr(struct etr_eacr eacr) -{ - int dp_changed; - - if (memcmp(&etr_eacr, &eacr, sizeof(eacr)) == 0) - /* No change, return. */ - return; - /* - * The disable of an active port of the change of the data port - * bit can/will cause a change in the data port. - */ - dp_changed = etr_eacr.e0 > eacr.e0 || etr_eacr.e1 > eacr.e1 || - (etr_eacr.dp ^ eacr.dp) != 0; - etr_eacr = eacr; - etr_setr(&etr_eacr); - if (dp_changed) - etr_tolec = get_clock(); -} - -/* - * ETR work. In this function you'll find the main logic. In - * particular this is the only function that calls etr_update_eacr(), - * it "controls" the etr control register. - */ -static void etr_work_fn(struct work_struct *work) -{ - unsigned long long now; - struct etr_eacr eacr; - struct etr_aib aib; - int sync_port; - - /* prevent multiple execution. */ - mutex_lock(&etr_work_mutex); - - /* Create working copy of etr_eacr. */ - eacr = etr_eacr; - - /* Check for the different events and their immediate effects. */ - eacr = etr_handle_events(eacr); - - /* Check if ETR is supposed to be active. */ - eacr.ea = eacr.p0 || eacr.p1; - if (!eacr.ea) { - /* Both ports offline. Reset everything. */ - eacr.dp = eacr.es = eacr.sl = 0; - on_each_cpu(disable_sync_clock, NULL, 1); - del_timer_sync(&etr_timer); - etr_update_eacr(eacr); - goto out_unlock; - } - - /* Store aib to get the current ETR status word. */ - BUG_ON(etr_stetr(&aib) != 0); - etr_port0.esw = etr_port1.esw = aib.esw; /* Copy status word. */ - now = get_clock(); - - /* - * Update the port information if the last stepping port change - * or data port change is older than 1.6 seconds. - */ - if (now >= etr_tolec + (1600000 << 12)) - eacr = etr_handle_update(&aib, eacr); - - /* - * Select ports to enable. The preferred synchronization mode is PPS. - * If a port can be enabled depends on a number of things: - * 1) The port needs to be online and uptodate. A port is not - * disabled just because it is not uptodate, but it is only - * enabled if it is uptodate. - * 2) The port needs to have the same mode (pps / etr). - * 3) The port needs to be usable -> etr_port_valid() == 1 - * 4) To enable the second port the clock needs to be in sync. - * 5) If both ports are useable and are ETR ports, the network id - * has to be the same. - * The eacr.sl bit is used to indicate etr mode vs. pps mode. - */ - if (eacr.p0 && aib.esw.psc0 == etr_lpsc_pps_mode) { - eacr.sl = 0; - eacr.e0 = 1; - if (!etr_mode_is_pps(etr_eacr)) - eacr.es = 0; - if (!eacr.es || !eacr.p1 || aib.esw.psc1 != etr_lpsc_pps_mode) - eacr.e1 = 0; - // FIXME: uptodate checks ? - else if (etr_port0_uptodate && etr_port1_uptodate) - eacr.e1 = 1; - sync_port = (etr_port0_uptodate && - etr_port_valid(&etr_port0, 0)) ? 0 : -1; - } else if (eacr.p1 && aib.esw.psc1 == etr_lpsc_pps_mode) { - eacr.sl = 0; - eacr.e0 = 0; - eacr.e1 = 1; - if (!etr_mode_is_pps(etr_eacr)) - eacr.es = 0; - sync_port = (etr_port1_uptodate && - etr_port_valid(&etr_port1, 1)) ? 1 : -1; - } else if (eacr.p0 && aib.esw.psc0 == etr_lpsc_operational_step) { - eacr.sl = 1; - eacr.e0 = 1; - if (!etr_mode_is_etr(etr_eacr)) - eacr.es = 0; - if (!eacr.es || !eacr.p1 || - aib.esw.psc1 != etr_lpsc_operational_alt) - eacr.e1 = 0; - else if (etr_port0_uptodate && etr_port1_uptodate && - etr_compare_network(&etr_port0, &etr_port1)) - eacr.e1 = 1; - sync_port = (etr_port0_uptodate && - etr_port_valid(&etr_port0, 0)) ? 0 : -1; - } else if (eacr.p1 && aib.esw.psc1 == etr_lpsc_operational_step) { - eacr.sl = 1; - eacr.e0 = 0; - eacr.e1 = 1; - if (!etr_mode_is_etr(etr_eacr)) - eacr.es = 0; - sync_port = (etr_port1_uptodate && - etr_port_valid(&etr_port1, 1)) ? 1 : -1; - } else { - /* Both ports not usable. */ - eacr.es = eacr.sl = 0; - sync_port = -1; - } - - /* - * If the clock is in sync just update the eacr and return. - * If there is no valid sync port wait for a port update. - */ - if ((eacr.es && check_sync_clock()) || sync_port < 0) { - etr_update_eacr(eacr); - etr_set_tolec_timeout(now); - goto out_unlock; - } - - /* - * Prepare control register for clock syncing - * (reset data port bit, set sync check control. - */ - eacr.dp = 0; - eacr.es = 1; - - /* - * Update eacr and try to synchronize the clock. If the update - * of eacr caused a stepping port switch (or if we have to - * assume that a stepping port switch has occurred) or the - * clock syncing failed, reset the sync check control bit - * and set up a timer to try again after 0.5 seconds - */ - etr_update_eacr(eacr); - if (now < etr_tolec + (1600000 << 12) || - etr_sync_clock_stop(&aib, sync_port) != 0) { - /* Sync failed. Try again in 1/2 second. */ - eacr.es = 0; - etr_update_eacr(eacr); - etr_set_sync_timeout(); - } else - etr_set_tolec_timeout(now); -out_unlock: - mutex_unlock(&etr_work_mutex); -} - -/* - * Sysfs interface functions - */ -static struct bus_type etr_subsys = { - .name = "etr", - .dev_name = "etr", -}; - -static struct device etr_port0_dev = { - .id = 0, - .bus = &etr_subsys, -}; - -static struct device etr_port1_dev = { - .id = 1, - .bus = &etr_subsys, -}; - -/* - * ETR subsys attributes - */ -static ssize_t etr_stepping_port_show(struct device *dev, - struct device_attribute *attr, - char *buf) -{ - return sprintf(buf, "%i\n", etr_port0.esw.p); -} - -static DEVICE_ATTR(stepping_port, 0400, etr_stepping_port_show, NULL); - -static ssize_t etr_stepping_mode_show(struct device *dev, - struct device_attribute *attr, - char *buf) -{ - char *mode_str; - - if (etr_mode_is_pps(etr_eacr)) - mode_str = "pps"; - else if (etr_mode_is_etr(etr_eacr)) - mode_str = "etr"; - else - mode_str = "local"; - return sprintf(buf, "%s\n", mode_str); -} - -static DEVICE_ATTR(stepping_mode, 0400, etr_stepping_mode_show, NULL); - -/* - * ETR port attributes - */ -static inline struct etr_aib *etr_aib_from_dev(struct device *dev) -{ - if (dev == &etr_port0_dev) - return etr_port0_online ? &etr_port0 : NULL; - else - return etr_port1_online ? &etr_port1 : NULL; -} - -static ssize_t etr_online_show(struct device *dev, - struct device_attribute *attr, - char *buf) -{ - unsigned int online; - - online = (dev == &etr_port0_dev) ? etr_port0_online : etr_port1_online; - return sprintf(buf, "%i\n", online); -} - -static ssize_t etr_online_store(struct device *dev, - struct device_attribute *attr, - const char *buf, size_t count) -{ - unsigned int value; - - value = simple_strtoul(buf, NULL, 0); - if (value != 0 && value != 1) - return -EINVAL; - if (!test_bit(CLOCK_SYNC_HAS_ETR, &clock_sync_flags)) - return -EOPNOTSUPP; - mutex_lock(&clock_sync_mutex); - if (dev == &etr_port0_dev) { - if (etr_port0_online == value) - goto out; /* Nothing to do. */ - etr_port0_online = value; - if (etr_port0_online && etr_port1_online) - set_bit(CLOCK_SYNC_ETR, &clock_sync_flags); - else - clear_bit(CLOCK_SYNC_ETR, &clock_sync_flags); - set_bit(ETR_EVENT_PORT0_CHANGE, &etr_events); - queue_work(time_sync_wq, &etr_work); - } else { - if (etr_port1_online == value) - goto out; /* Nothing to do. */ - etr_port1_online = value; - if (etr_port0_online && etr_port1_online) - set_bit(CLOCK_SYNC_ETR, &clock_sync_flags); - else - clear_bit(CLOCK_SYNC_ETR, &clock_sync_flags); - set_bit(ETR_EVENT_PORT1_CHANGE, &etr_events); - queue_work(time_sync_wq, &etr_work); - } -out: - mutex_unlock(&clock_sync_mutex); - return count; -} - -static DEVICE_ATTR(online, 0600, etr_online_show, etr_online_store); - -static ssize_t etr_stepping_control_show(struct device *dev, - struct device_attribute *attr, - char *buf) -{ - return sprintf(buf, "%i\n", (dev == &etr_port0_dev) ? - etr_eacr.e0 : etr_eacr.e1); -} - -static DEVICE_ATTR(stepping_control, 0400, etr_stepping_control_show, NULL); - -static ssize_t etr_mode_code_show(struct device *dev, - struct device_attribute *attr, char *buf) -{ - if (!etr_port0_online && !etr_port1_online) - /* Status word is not uptodate if both ports are offline. */ - return -ENODATA; - return sprintf(buf, "%i\n", (dev == &etr_port0_dev) ? - etr_port0.esw.psc0 : etr_port0.esw.psc1); -} - -static DEVICE_ATTR(state_code, 0400, etr_mode_code_show, NULL); - -static ssize_t etr_untuned_show(struct device *dev, - struct device_attribute *attr, char *buf) -{ - struct etr_aib *aib = etr_aib_from_dev(dev); - - if (!aib || !aib->slsw.v1) - return -ENODATA; - return sprintf(buf, "%i\n", aib->edf1.u); -} - -static DEVICE_ATTR(untuned, 0400, etr_untuned_show, NULL); - -static ssize_t etr_network_id_show(struct device *dev, - struct device_attribute *attr, char *buf) -{ - struct etr_aib *aib = etr_aib_from_dev(dev); - - if (!aib || !aib->slsw.v1) - return -ENODATA; - return sprintf(buf, "%i\n", aib->edf1.net_id); -} - -static DEVICE_ATTR(network, 0400, etr_network_id_show, NULL); - -static ssize_t etr_id_show(struct device *dev, - struct device_attribute *attr, char *buf) -{ - struct etr_aib *aib = etr_aib_from_dev(dev); - - if (!aib || !aib->slsw.v1) - return -ENODATA; - return sprintf(buf, "%i\n", aib->edf1.etr_id); -} - -static DEVICE_ATTR(id, 0400, etr_id_show, NULL); - -static ssize_t etr_port_number_show(struct device *dev, - struct device_attribute *attr, char *buf) -{ - struct etr_aib *aib = etr_aib_from_dev(dev); - - if (!aib || !aib->slsw.v1) - return -ENODATA; - return sprintf(buf, "%i\n", aib->edf1.etr_pn); -} - -static DEVICE_ATTR(port, 0400, etr_port_number_show, NULL); - -static ssize_t etr_coupled_show(struct device *dev, - struct device_attribute *attr, char *buf) -{ - struct etr_aib *aib = etr_aib_from_dev(dev); - - if (!aib || !aib->slsw.v3) - return -ENODATA; - return sprintf(buf, "%i\n", aib->edf3.c); -} - -static DEVICE_ATTR(coupled, 0400, etr_coupled_show, NULL); - -static ssize_t etr_local_time_show(struct device *dev, - struct device_attribute *attr, char *buf) -{ - struct etr_aib *aib = etr_aib_from_dev(dev); - - if (!aib || !aib->slsw.v3) - return -ENODATA; - return sprintf(buf, "%i\n", aib->edf3.blto); -} - -static DEVICE_ATTR(local_time, 0400, etr_local_time_show, NULL); - -static ssize_t etr_utc_offset_show(struct device *dev, - struct device_attribute *attr, char *buf) -{ - struct etr_aib *aib = etr_aib_from_dev(dev); - - if (!aib || !aib->slsw.v3) - return -ENODATA; - return sprintf(buf, "%i\n", aib->edf3.buo); -} - -static DEVICE_ATTR(utc_offset, 0400, etr_utc_offset_show, NULL); - -static struct device_attribute *etr_port_attributes[] = { - &dev_attr_online, - &dev_attr_stepping_control, - &dev_attr_state_code, - &dev_attr_untuned, - &dev_attr_network, - &dev_attr_id, - &dev_attr_port, - &dev_attr_coupled, - &dev_attr_local_time, - &dev_attr_utc_offset, - NULL -}; - -static int __init etr_register_port(struct device *dev) -{ - struct device_attribute **attr; - int rc; - - rc = device_register(dev); - if (rc) - goto out; - for (attr = etr_port_attributes; *attr; attr++) { - rc = device_create_file(dev, *attr); - if (rc) - goto out_unreg; - } - return 0; -out_unreg: - for (; attr >= etr_port_attributes; attr--) - device_remove_file(dev, *attr); - device_unregister(dev); -out: - return rc; -} - -static void __init etr_unregister_port(struct device *dev) -{ - struct device_attribute **attr; - - for (attr = etr_port_attributes; *attr; attr++) - device_remove_file(dev, *attr); - device_unregister(dev); -} - -static int __init etr_init_sysfs(void) -{ - int rc; - - rc = subsys_system_register(&etr_subsys, NULL); - if (rc) - goto out; - rc = device_create_file(etr_subsys.dev_root, &dev_attr_stepping_port); - if (rc) - goto out_unreg_subsys; - rc = device_create_file(etr_subsys.dev_root, &dev_attr_stepping_mode); - if (rc) - goto out_remove_stepping_port; - rc = etr_register_port(&etr_port0_dev); - if (rc) - goto out_remove_stepping_mode; - rc = etr_register_port(&etr_port1_dev); - if (rc) - goto out_remove_port0; - return 0; - -out_remove_port0: - etr_unregister_port(&etr_port0_dev); -out_remove_stepping_mode: - device_remove_file(etr_subsys.dev_root, &dev_attr_stepping_mode); -out_remove_stepping_port: - device_remove_file(etr_subsys.dev_root, &dev_attr_stepping_port); -out_unreg_subsys: - bus_unregister(&etr_subsys); -out: - return rc; -} - -device_initcall(etr_init_sysfs); - -/* - * Server Time Protocol (STP) code. - */ -static int stp_online; -static struct stp_sstpi stp_info; -static void *stp_page; - -static void stp_work_fn(struct work_struct *work); -static DEFINE_MUTEX(stp_work_mutex); -static DECLARE_WORK(stp_work, stp_work_fn); -static struct timer_list stp_timer; - -static int __init early_parse_stp(char *p) -{ - if (strncmp(p, "off", 3) == 0) - stp_online = 0; - else if (strncmp(p, "on", 2) == 0) - stp_online = 1; - return 0; -} -early_param("stp", early_parse_stp); - -/* - * Reset STP attachment. - */ -static void __init stp_reset(void) -{ - int rc; - - stp_page = (void *) get_zeroed_page(GFP_ATOMIC); - rc = chsc_sstpc(stp_page, STP_OP_CTRL, 0x0000); - if (rc == 0) - set_bit(CLOCK_SYNC_HAS_STP, &clock_sync_flags); - else if (stp_online) { - pr_warning("The real or virtual hardware system does " - "not provide an STP interface\n"); - free_page((unsigned long) stp_page); - stp_page = NULL; - stp_online = 0; - } -} - -static void stp_timeout(unsigned long dummy) -{ - queue_work(time_sync_wq, &stp_work); -} - -static int __init stp_init(void) -{ - if (!test_bit(CLOCK_SYNC_HAS_STP, &clock_sync_flags)) - return 0; - setup_timer(&stp_timer, stp_timeout, 0UL); - time_init_wq(); - if (!stp_online) - return 0; - queue_work(time_sync_wq, &stp_work); - return 0; -} - -arch_initcall(stp_init); - -/* - * STP timing alert. There are three causes: - * 1) timing status change - * 2) link availability change - * 3) time control parameter change - * In all three cases we are only interested in the clock source state. - * If a STP clock source is now available use it. - */ -static void stp_timing_alert(struct stp_irq_parm *intparm) -{ - if (intparm->tsc || intparm->lac || intparm->tcpc) - queue_work(time_sync_wq, &stp_work); -} - -/* - * STP sync check machine check. This is called when the timing state - * changes from the synchronized state to the unsynchronized state. - * After a STP sync check the clock is not in sync. The machine check - * is broadcasted to all cpus at the same time. - */ -void stp_sync_check(void) -{ - disable_sync_clock(NULL); - queue_work(time_sync_wq, &stp_work); -} - -/* - * STP island condition machine check. This is called when an attached - * server attempts to communicate over an STP link and the servers - * have matching CTN ids and have a valid stratum-1 configuration - * but the configurations do not match. - */ -void stp_island_check(void) -{ - disable_sync_clock(NULL); - queue_work(time_sync_wq, &stp_work); -} - - -static int stp_sync_clock(void *data) -{ - static int first; - unsigned long long old_clock, delta; - struct clock_sync_data *stp_sync; - int rc; - - stp_sync = data; - - if (xchg(&first, 1) == 1) { - /* Slave */ - clock_sync_cpu(stp_sync); - return 0; - } - - /* Wait until all other cpus entered the sync function. */ - while (atomic_read(&stp_sync->cpus) != 0) - cpu_relax(); - - enable_sync_clock(); - - rc = 0; - if (stp_info.todoff[0] || stp_info.todoff[1] || - stp_info.todoff[2] || stp_info.todoff[3] || - stp_info.tmd != 2) { - old_clock = get_clock(); - rc = chsc_sstpc(stp_page, STP_OP_SYNC, 0); - if (rc == 0) { - delta = adjust_time(old_clock, get_clock(), 0); - fixup_clock_comparator(delta); - rc = chsc_sstpi(stp_page, &stp_info, - sizeof(struct stp_sstpi)); - if (rc == 0 && stp_info.tmd != 2) - rc = -EAGAIN; - } - } - if (rc) { - disable_sync_clock(NULL); - stp_sync->in_sync = -EAGAIN; - } else - stp_sync->in_sync = 1; - xchg(&first, 0); - return 0; -} - -/* - * STP work. Check for the STP state and take over the clock - * synchronization if the STP clock source is usable. - */ -static void stp_work_fn(struct work_struct *work) -{ - struct clock_sync_data stp_sync; - int rc; - - /* prevent multiple execution. */ - mutex_lock(&stp_work_mutex); - - if (!stp_online) { - chsc_sstpc(stp_page, STP_OP_CTRL, 0x0000); - del_timer_sync(&stp_timer); - goto out_unlock; - } - - rc = chsc_sstpc(stp_page, STP_OP_CTRL, 0xb0e0); - if (rc) - goto out_unlock; - - rc = chsc_sstpi(stp_page, &stp_info, sizeof(struct stp_sstpi)); - if (rc || stp_info.c == 0) - goto out_unlock; - - /* Skip synchronization if the clock is already in sync. */ - if (check_sync_clock()) - goto out_unlock; - - memset(&stp_sync, 0, sizeof(stp_sync)); - get_online_cpus(); - atomic_set(&stp_sync.cpus, num_online_cpus() - 1); - stop_machine(stp_sync_clock, &stp_sync, cpu_online_mask); - put_online_cpus(); - - if (!check_sync_clock()) - /* - * There is a usable clock but the synchonization failed. - * Retry after a second. - */ - mod_timer(&stp_timer, jiffies + HZ); - -out_unlock: - mutex_unlock(&stp_work_mutex); -} - -/* - * STP subsys sysfs interface functions - */ -static struct bus_type stp_subsys = { - .name = "stp", - .dev_name = "stp", -}; - -static ssize_t stp_ctn_id_show(struct device *dev, - struct device_attribute *attr, - char *buf) -{ - if (!stp_online) - return -ENODATA; - return sprintf(buf, "%016llx\n", - *(unsigned long long *) stp_info.ctnid); -} - -static DEVICE_ATTR(ctn_id, 0400, stp_ctn_id_show, NULL); - -static ssize_t stp_ctn_type_show(struct device *dev, - struct device_attribute *attr, - char *buf) -{ - if (!stp_online) - return -ENODATA; - return sprintf(buf, "%i\n", stp_info.ctn); -} - -static DEVICE_ATTR(ctn_type, 0400, stp_ctn_type_show, NULL); - -static ssize_t stp_dst_offset_show(struct device *dev, - struct device_attribute *attr, - char *buf) -{ - if (!stp_online || !(stp_info.vbits & 0x2000)) - return -ENODATA; - return sprintf(buf, "%i\n", (int)(s16) stp_info.dsto); -} - -static DEVICE_ATTR(dst_offset, 0400, stp_dst_offset_show, NULL); - -static ssize_t stp_leap_seconds_show(struct device *dev, - struct device_attribute *attr, - char *buf) -{ - if (!stp_online || !(stp_info.vbits & 0x8000)) - return -ENODATA; - return sprintf(buf, "%i\n", (int)(s16) stp_info.leaps); -} - -static DEVICE_ATTR(leap_seconds, 0400, stp_leap_seconds_show, NULL); - -static ssize_t stp_stratum_show(struct device *dev, - struct device_attribute *attr, - char *buf) -{ - if (!stp_online) - return -ENODATA; - return sprintf(buf, "%i\n", (int)(s16) stp_info.stratum); -} - -static DEVICE_ATTR(stratum, 0400, stp_stratum_show, NULL); - -static ssize_t stp_time_offset_show(struct device *dev, - struct device_attribute *attr, - char *buf) -{ - if (!stp_online || !(stp_info.vbits & 0x0800)) - return -ENODATA; - return sprintf(buf, "%i\n", (int) stp_info.tto); -} - -static DEVICE_ATTR(time_offset, 0400, stp_time_offset_show, NULL); - -static ssize_t stp_time_zone_offset_show(struct device *dev, - struct device_attribute *attr, - char *buf) -{ - if (!stp_online || !(stp_info.vbits & 0x4000)) - return -ENODATA; - return sprintf(buf, "%i\n", (int)(s16) stp_info.tzo); -} - -static DEVICE_ATTR(time_zone_offset, 0400, - stp_time_zone_offset_show, NULL); - -static ssize_t stp_timing_mode_show(struct device *dev, - struct device_attribute *attr, - char *buf) -{ - if (!stp_online) - return -ENODATA; - return sprintf(buf, "%i\n", stp_info.tmd); -} - -static DEVICE_ATTR(timing_mode, 0400, stp_timing_mode_show, NULL); - -static ssize_t stp_timing_state_show(struct device *dev, - struct device_attribute *attr, - char *buf) -{ - if (!stp_online) - return -ENODATA; - return sprintf(buf, "%i\n", stp_info.tst); -} - -static DEVICE_ATTR(timing_state, 0400, stp_timing_state_show, NULL); - -static ssize_t stp_online_show(struct device *dev, - struct device_attribute *attr, - char *buf) -{ - return sprintf(buf, "%i\n", stp_online); -} - -static ssize_t stp_online_store(struct device *dev, - struct device_attribute *attr, - const char *buf, size_t count) -{ - unsigned int value; - - value = simple_strtoul(buf, NULL, 0); - if (value != 0 && value != 1) - return -EINVAL; - if (!test_bit(CLOCK_SYNC_HAS_STP, &clock_sync_flags)) - return -EOPNOTSUPP; - mutex_lock(&clock_sync_mutex); - stp_online = value; - if (stp_online) - set_bit(CLOCK_SYNC_STP, &clock_sync_flags); - else - clear_bit(CLOCK_SYNC_STP, &clock_sync_flags); - queue_work(time_sync_wq, &stp_work); - mutex_unlock(&clock_sync_mutex); - return count; -} - -/* - * Can't use DEVICE_ATTR because the attribute should be named - * stp/online but dev_attr_online already exists in this file .. - */ -static struct device_attribute dev_attr_stp_online = { - .attr = { .name = "online", .mode = 0600 }, - .show = stp_online_show, - .store = stp_online_store, -}; - -static struct device_attribute *stp_attributes[] = { - &dev_attr_ctn_id, - &dev_attr_ctn_type, - &dev_attr_dst_offset, - &dev_attr_leap_seconds, - &dev_attr_stp_online, - &dev_attr_stratum, - &dev_attr_time_offset, - &dev_attr_time_zone_offset, - &dev_attr_timing_mode, - &dev_attr_timing_state, - NULL -}; - -static int __init stp_init_sysfs(void) -{ - struct device_attribute **attr; - int rc; - - rc = subsys_system_register(&stp_subsys, NULL); - if (rc) - goto out; - for (attr = stp_attributes; *attr; attr++) { - rc = device_create_file(stp_subsys.dev_root, *attr); - if (rc) - goto out_unreg; - } - return 0; -out_unreg: - for (; attr >= stp_attributes; attr--) - device_remove_file(stp_subsys.dev_root, *attr); - bus_unregister(&stp_subsys); -out: - return rc; -} - -device_initcall(stp_init_sysfs); diff --git a/ANDROID_3.4.5/arch/s390/kernel/topology.c b/ANDROID_3.4.5/arch/s390/kernel/topology.c deleted file mode 100644 index 4f8dc942..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/topology.c +++ /dev/null @@ -1,465 +0,0 @@ -/* - * Copyright IBM Corp. 2007,2011 - * Author(s): Heiko Carstens <heiko.carstens@de.ibm.com> - */ - -#define KMSG_COMPONENT "cpu" -#define pr_fmt(fmt) KMSG_COMPONENT ": " fmt - -#include <linux/workqueue.h> -#include <linux/bootmem.h> -#include <linux/cpuset.h> -#include <linux/device.h> -#include <linux/kernel.h> -#include <linux/sched.h> -#include <linux/init.h> -#include <linux/delay.h> -#include <linux/cpu.h> -#include <linux/smp.h> -#include <linux/mm.h> - -#define PTF_HORIZONTAL (0UL) -#define PTF_VERTICAL (1UL) -#define PTF_CHECK (2UL) - -struct mask_info { - struct mask_info *next; - unsigned char id; - cpumask_t mask; -}; - -static int topology_enabled = 1; -static void topology_work_fn(struct work_struct *work); -static struct sysinfo_15_1_x *tl_info; -static void set_topology_timer(void); -static DECLARE_WORK(topology_work, topology_work_fn); -/* topology_lock protects the core linked list */ -static DEFINE_SPINLOCK(topology_lock); - -static struct mask_info core_info; -cpumask_t cpu_core_map[NR_CPUS]; -unsigned char cpu_core_id[NR_CPUS]; - -static struct mask_info book_info; -cpumask_t cpu_book_map[NR_CPUS]; -unsigned char cpu_book_id[NR_CPUS]; - -/* smp_cpu_state_mutex must be held when accessing this array */ -int cpu_polarization[NR_CPUS]; - -static cpumask_t cpu_group_map(struct mask_info *info, unsigned int cpu) -{ - cpumask_t mask; - - cpumask_clear(&mask); - if (!topology_enabled || !MACHINE_HAS_TOPOLOGY) { - cpumask_copy(&mask, cpumask_of(cpu)); - return mask; - } - while (info) { - if (cpumask_test_cpu(cpu, &info->mask)) { - mask = info->mask; - break; - } - info = info->next; - } - if (cpumask_empty(&mask)) - cpumask_copy(&mask, cpumask_of(cpu)); - return mask; -} - -static struct mask_info *add_cpus_to_mask(struct topology_cpu *tl_cpu, - struct mask_info *book, - struct mask_info *core, - int one_core_per_cpu) -{ - unsigned int cpu; - - for (cpu = find_first_bit(&tl_cpu->mask[0], TOPOLOGY_CPU_BITS); - cpu < TOPOLOGY_CPU_BITS; - cpu = find_next_bit(&tl_cpu->mask[0], TOPOLOGY_CPU_BITS, cpu + 1)) - { - unsigned int rcpu; - int lcpu; - - rcpu = TOPOLOGY_CPU_BITS - 1 - cpu + tl_cpu->origin; - lcpu = smp_find_processor_id(rcpu); - if (lcpu >= 0) { - cpumask_set_cpu(lcpu, &book->mask); - cpu_book_id[lcpu] = book->id; - cpumask_set_cpu(lcpu, &core->mask); - if (one_core_per_cpu) { - cpu_core_id[lcpu] = rcpu; - core = core->next; - } else { - cpu_core_id[lcpu] = core->id; - } - cpu_set_polarization(lcpu, tl_cpu->pp); - } - } - return core; -} - -static void clear_masks(void) -{ - struct mask_info *info; - - info = &core_info; - while (info) { - cpumask_clear(&info->mask); - info = info->next; - } - info = &book_info; - while (info) { - cpumask_clear(&info->mask); - info = info->next; - } -} - -static union topology_entry *next_tle(union topology_entry *tle) -{ - if (!tle->nl) - return (union topology_entry *)((struct topology_cpu *)tle + 1); - return (union topology_entry *)((struct topology_container *)tle + 1); -} - -static void __tl_to_cores_generic(struct sysinfo_15_1_x *info) -{ - struct mask_info *core = &core_info; - struct mask_info *book = &book_info; - union topology_entry *tle, *end; - - tle = info->tle; - end = (union topology_entry *)((unsigned long)info + info->length); - while (tle < end) { - switch (tle->nl) { - case 2: - book = book->next; - book->id = tle->container.id; - break; - case 1: - core = core->next; - core->id = tle->container.id; - break; - case 0: - add_cpus_to_mask(&tle->cpu, book, core, 0); - break; - default: - clear_masks(); - return; - } - tle = next_tle(tle); - } -} - -static void __tl_to_cores_z10(struct sysinfo_15_1_x *info) -{ - struct mask_info *core = &core_info; - struct mask_info *book = &book_info; - union topology_entry *tle, *end; - - tle = info->tle; - end = (union topology_entry *)((unsigned long)info + info->length); - while (tle < end) { - switch (tle->nl) { - case 1: - book = book->next; - book->id = tle->container.id; - break; - case 0: - core = add_cpus_to_mask(&tle->cpu, book, core, 1); - break; - default: - clear_masks(); - return; - } - tle = next_tle(tle); - } -} - -static void tl_to_cores(struct sysinfo_15_1_x *info) -{ - struct cpuid cpu_id; - - get_cpu_id(&cpu_id); - spin_lock_irq(&topology_lock); - clear_masks(); - switch (cpu_id.machine) { - case 0x2097: - case 0x2098: - __tl_to_cores_z10(info); - break; - default: - __tl_to_cores_generic(info); - } - spin_unlock_irq(&topology_lock); -} - -static void topology_update_polarization_simple(void) -{ - int cpu; - - mutex_lock(&smp_cpu_state_mutex); - for_each_possible_cpu(cpu) - cpu_set_polarization(cpu, POLARIZATION_HRZ); - mutex_unlock(&smp_cpu_state_mutex); -} - -static int ptf(unsigned long fc) -{ - int rc; - - asm volatile( - " .insn rre,0xb9a20000,%1,%1\n" - " ipm %0\n" - " srl %0,28\n" - : "=d" (rc) - : "d" (fc) : "cc"); - return rc; -} - -int topology_set_cpu_management(int fc) -{ - int cpu, rc; - - if (!MACHINE_HAS_TOPOLOGY) - return -EOPNOTSUPP; - if (fc) - rc = ptf(PTF_VERTICAL); - else - rc = ptf(PTF_HORIZONTAL); - if (rc) - return -EBUSY; - for_each_possible_cpu(cpu) - cpu_set_polarization(cpu, POLARIZATION_UNKNOWN); - return rc; -} - -static void update_cpu_core_map(void) -{ - unsigned long flags; - int cpu; - - spin_lock_irqsave(&topology_lock, flags); - for_each_possible_cpu(cpu) { - cpu_core_map[cpu] = cpu_group_map(&core_info, cpu); - cpu_book_map[cpu] = cpu_group_map(&book_info, cpu); - } - spin_unlock_irqrestore(&topology_lock, flags); -} - -void store_topology(struct sysinfo_15_1_x *info) -{ - int rc; - - rc = stsi(info, 15, 1, 3); - if (rc != -ENOSYS) - return; - stsi(info, 15, 1, 2); -} - -int arch_update_cpu_topology(void) -{ - struct sysinfo_15_1_x *info = tl_info; - struct device *dev; - int cpu; - - if (!MACHINE_HAS_TOPOLOGY) { - update_cpu_core_map(); - topology_update_polarization_simple(); - return 0; - } - store_topology(info); - tl_to_cores(info); - update_cpu_core_map(); - for_each_online_cpu(cpu) { - dev = get_cpu_device(cpu); - kobject_uevent(&dev->kobj, KOBJ_CHANGE); - } - return 1; -} - -static void topology_work_fn(struct work_struct *work) -{ - rebuild_sched_domains(); -} - -void topology_schedule_update(void) -{ - schedule_work(&topology_work); -} - -static void topology_timer_fn(unsigned long ignored) -{ - if (ptf(PTF_CHECK)) - topology_schedule_update(); - set_topology_timer(); -} - -static struct timer_list topology_timer = - TIMER_DEFERRED_INITIALIZER(topology_timer_fn, 0, 0); - -static atomic_t topology_poll = ATOMIC_INIT(0); - -static void set_topology_timer(void) -{ - if (atomic_add_unless(&topology_poll, -1, 0)) - mod_timer(&topology_timer, jiffies + HZ / 10); - else - mod_timer(&topology_timer, jiffies + HZ * 60); -} - -void topology_expect_change(void) -{ - if (!MACHINE_HAS_TOPOLOGY) - return; - /* This is racy, but it doesn't matter since it is just a heuristic. - * Worst case is that we poll in a higher frequency for a bit longer. - */ - if (atomic_read(&topology_poll) > 60) - return; - atomic_add(60, &topology_poll); - set_topology_timer(); -} - -static int __init early_parse_topology(char *p) -{ - if (strncmp(p, "off", 3)) - return 0; - topology_enabled = 0; - return 0; -} -early_param("topology", early_parse_topology); - -static void __init alloc_masks(struct sysinfo_15_1_x *info, - struct mask_info *mask, int offset) -{ - int i, nr_masks; - - nr_masks = info->mag[TOPOLOGY_NR_MAG - offset]; - for (i = 0; i < info->mnest - offset; i++) - nr_masks *= info->mag[TOPOLOGY_NR_MAG - offset - 1 - i]; - nr_masks = max(nr_masks, 1); - for (i = 0; i < nr_masks; i++) { - mask->next = alloc_bootmem(sizeof(struct mask_info)); - mask = mask->next; - } -} - -void __init s390_init_cpu_topology(void) -{ - struct sysinfo_15_1_x *info; - int i; - - if (!MACHINE_HAS_TOPOLOGY) - return; - tl_info = alloc_bootmem_pages(PAGE_SIZE); - info = tl_info; - store_topology(info); - pr_info("The CPU configuration topology of the machine is:"); - for (i = 0; i < TOPOLOGY_NR_MAG; i++) - printk(KERN_CONT " %d", info->mag[i]); - printk(KERN_CONT " / %d\n", info->mnest); - alloc_masks(info, &core_info, 1); - alloc_masks(info, &book_info, 2); -} - -static int cpu_management; - -static ssize_t dispatching_show(struct device *dev, - struct device_attribute *attr, - char *buf) -{ - ssize_t count; - - mutex_lock(&smp_cpu_state_mutex); - count = sprintf(buf, "%d\n", cpu_management); - mutex_unlock(&smp_cpu_state_mutex); - return count; -} - -static ssize_t dispatching_store(struct device *dev, - struct device_attribute *attr, - const char *buf, - size_t count) -{ - int val, rc; - char delim; - - if (sscanf(buf, "%d %c", &val, &delim) != 1) - return -EINVAL; - if (val != 0 && val != 1) - return -EINVAL; - rc = 0; - get_online_cpus(); - mutex_lock(&smp_cpu_state_mutex); - if (cpu_management == val) - goto out; - rc = topology_set_cpu_management(val); - if (rc) - goto out; - cpu_management = val; - topology_expect_change(); -out: - mutex_unlock(&smp_cpu_state_mutex); - put_online_cpus(); - return rc ? rc : count; -} -static DEVICE_ATTR(dispatching, 0644, dispatching_show, - dispatching_store); - -static ssize_t cpu_polarization_show(struct device *dev, - struct device_attribute *attr, char *buf) -{ - int cpu = dev->id; - ssize_t count; - - mutex_lock(&smp_cpu_state_mutex); - switch (cpu_read_polarization(cpu)) { - case POLARIZATION_HRZ: - count = sprintf(buf, "horizontal\n"); - break; - case POLARIZATION_VL: - count = sprintf(buf, "vertical:low\n"); - break; - case POLARIZATION_VM: - count = sprintf(buf, "vertical:medium\n"); - break; - case POLARIZATION_VH: - count = sprintf(buf, "vertical:high\n"); - break; - default: - count = sprintf(buf, "unknown\n"); - break; - } - mutex_unlock(&smp_cpu_state_mutex); - return count; -} -static DEVICE_ATTR(polarization, 0444, cpu_polarization_show, NULL); - -static struct attribute *topology_cpu_attrs[] = { - &dev_attr_polarization.attr, - NULL, -}; - -static struct attribute_group topology_cpu_attr_group = { - .attrs = topology_cpu_attrs, -}; - -int topology_cpu_init(struct cpu *cpu) -{ - return sysfs_create_group(&cpu->dev.kobj, &topology_cpu_attr_group); -} - -static int __init topology_init(void) -{ - if (!MACHINE_HAS_TOPOLOGY) { - topology_update_polarization_simple(); - goto out; - } - set_topology_timer(); -out: - update_cpu_core_map(); - return device_create_file(cpu_subsys.dev_root, &dev_attr_dispatching); -} -device_initcall(topology_init); diff --git a/ANDROID_3.4.5/arch/s390/kernel/traps.c b/ANDROID_3.4.5/arch/s390/kernel/traps.c deleted file mode 100644 index 77cdf423..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/traps.c +++ /dev/null @@ -1,656 +0,0 @@ -/* - * arch/s390/kernel/traps.c - * - * S390 version - * Copyright (C) 1999,2000 IBM Deutschland Entwicklung GmbH, IBM Corporation - * Author(s): Martin Schwidefsky (schwidefsky@de.ibm.com), - * Denis Joseph Barrow (djbarrow@de.ibm.com,barrow_dj@yahoo.com), - * - * Derived from "arch/i386/kernel/traps.c" - * Copyright (C) 1991, 1992 Linus Torvalds - */ - -/* - * 'Traps.c' handles hardware traps and faults after we have saved some - * state in 'asm.s'. - */ -#include <linux/sched.h> -#include <linux/kernel.h> -#include <linux/string.h> -#include <linux/errno.h> -#include <linux/ptrace.h> -#include <linux/timer.h> -#include <linux/mm.h> -#include <linux/smp.h> -#include <linux/init.h> -#include <linux/interrupt.h> -#include <linux/seq_file.h> -#include <linux/delay.h> -#include <linux/module.h> -#include <linux/kdebug.h> -#include <linux/kallsyms.h> -#include <linux/reboot.h> -#include <linux/kprobes.h> -#include <linux/bug.h> -#include <linux/utsname.h> -#include <asm/uaccess.h> -#include <asm/io.h> -#include <linux/atomic.h> -#include <asm/mathemu.h> -#include <asm/cpcmd.h> -#include <asm/lowcore.h> -#include <asm/debug.h> -#include <asm/ipl.h> -#include "entry.h" - -void (*pgm_check_table[128])(struct pt_regs *regs); - -int show_unhandled_signals = 1; - -#define stack_pointer ({ void **sp; asm("la %0,0(15)" : "=&d" (sp)); sp; }) - -#ifndef CONFIG_64BIT -#define LONG "%08lx " -#define FOURLONG "%08lx %08lx %08lx %08lx\n" -static int kstack_depth_to_print = 12; -#else /* CONFIG_64BIT */ -#define LONG "%016lx " -#define FOURLONG "%016lx %016lx %016lx %016lx\n" -static int kstack_depth_to_print = 20; -#endif /* CONFIG_64BIT */ - -/* - * For show_trace we have tree different stack to consider: - * - the panic stack which is used if the kernel stack has overflown - * - the asynchronous interrupt stack (cpu related) - * - the synchronous kernel stack (process related) - * The stack trace can start at any of the three stack and can potentially - * touch all of them. The order is: panic stack, async stack, sync stack. - */ -static unsigned long -__show_trace(unsigned long sp, unsigned long low, unsigned long high) -{ - struct stack_frame *sf; - struct pt_regs *regs; - - while (1) { - sp = sp & PSW_ADDR_INSN; - if (sp < low || sp > high - sizeof(*sf)) - return sp; - sf = (struct stack_frame *) sp; - printk("([<%016lx>] ", sf->gprs[8] & PSW_ADDR_INSN); - print_symbol("%s)\n", sf->gprs[8] & PSW_ADDR_INSN); - /* Follow the backchain. */ - while (1) { - low = sp; - sp = sf->back_chain & PSW_ADDR_INSN; - if (!sp) - break; - if (sp <= low || sp > high - sizeof(*sf)) - return sp; - sf = (struct stack_frame *) sp; - printk(" [<%016lx>] ", sf->gprs[8] & PSW_ADDR_INSN); - print_symbol("%s\n", sf->gprs[8] & PSW_ADDR_INSN); - } - /* Zero backchain detected, check for interrupt frame. */ - sp = (unsigned long) (sf + 1); - if (sp <= low || sp > high - sizeof(*regs)) - return sp; - regs = (struct pt_regs *) sp; - printk(" [<%016lx>] ", regs->psw.addr & PSW_ADDR_INSN); - print_symbol("%s\n", regs->psw.addr & PSW_ADDR_INSN); - low = sp; - sp = regs->gprs[15]; - } -} - -static void show_trace(struct task_struct *task, unsigned long *stack) -{ - register unsigned long __r15 asm ("15"); - unsigned long sp; - - sp = (unsigned long) stack; - if (!sp) - sp = task ? task->thread.ksp : __r15; - printk("Call Trace:\n"); -#ifdef CONFIG_CHECK_STACK - sp = __show_trace(sp, S390_lowcore.panic_stack - 4096, - S390_lowcore.panic_stack); -#endif - sp = __show_trace(sp, S390_lowcore.async_stack - ASYNC_SIZE, - S390_lowcore.async_stack); - if (task) - __show_trace(sp, (unsigned long) task_stack_page(task), - (unsigned long) task_stack_page(task) + THREAD_SIZE); - else - __show_trace(sp, S390_lowcore.thread_info, - S390_lowcore.thread_info + THREAD_SIZE); - if (!task) - task = current; - debug_show_held_locks(task); -} - -void show_stack(struct task_struct *task, unsigned long *sp) -{ - register unsigned long * __r15 asm ("15"); - unsigned long *stack; - int i; - - if (!sp) - stack = task ? (unsigned long *) task->thread.ksp : __r15; - else - stack = sp; - - for (i = 0; i < kstack_depth_to_print; i++) { - if (((addr_t) stack & (THREAD_SIZE-1)) == 0) - break; - if ((i * sizeof(long) % 32) == 0) - printk("%s ", i == 0 ? "" : "\n"); - printk(LONG, *stack++); - } - printk("\n"); - show_trace(task, sp); -} - -static void show_last_breaking_event(struct pt_regs *regs) -{ -#ifdef CONFIG_64BIT - printk("Last Breaking-Event-Address:\n"); - printk(" [<%016lx>] ", regs->args[0] & PSW_ADDR_INSN); - print_symbol("%s\n", regs->args[0] & PSW_ADDR_INSN); -#endif -} - -/* - * The architecture-independent dump_stack generator - */ -void dump_stack(void) -{ - printk("CPU: %d %s %s %.*s\n", - task_thread_info(current)->cpu, print_tainted(), - init_utsname()->release, - (int)strcspn(init_utsname()->version, " "), - init_utsname()->version); - printk("Process %s (pid: %d, task: %p, ksp: %p)\n", - current->comm, current->pid, current, - (void *) current->thread.ksp); - show_stack(NULL, NULL); -} -EXPORT_SYMBOL(dump_stack); - -static inline int mask_bits(struct pt_regs *regs, unsigned long bits) -{ - return (regs->psw.mask & bits) / ((~bits + 1) & bits); -} - -void show_registers(struct pt_regs *regs) -{ - char *mode; - - mode = (regs->psw.mask & PSW_MASK_PSTATE) ? "User" : "Krnl"; - printk("%s PSW : %p %p", - mode, (void *) regs->psw.mask, - (void *) regs->psw.addr); - print_symbol(" (%s)\n", regs->psw.addr & PSW_ADDR_INSN); - printk(" R:%x T:%x IO:%x EX:%x Key:%x M:%x W:%x " - "P:%x AS:%x CC:%x PM:%x", mask_bits(regs, PSW_MASK_PER), - mask_bits(regs, PSW_MASK_DAT), mask_bits(regs, PSW_MASK_IO), - mask_bits(regs, PSW_MASK_EXT), mask_bits(regs, PSW_MASK_KEY), - mask_bits(regs, PSW_MASK_MCHECK), mask_bits(regs, PSW_MASK_WAIT), - mask_bits(regs, PSW_MASK_PSTATE), mask_bits(regs, PSW_MASK_ASC), - mask_bits(regs, PSW_MASK_CC), mask_bits(regs, PSW_MASK_PM)); -#ifdef CONFIG_64BIT - printk(" EA:%x", mask_bits(regs, PSW_MASK_EA | PSW_MASK_BA)); -#endif - printk("\n%s GPRS: " FOURLONG, mode, - regs->gprs[0], regs->gprs[1], regs->gprs[2], regs->gprs[3]); - printk(" " FOURLONG, - regs->gprs[4], regs->gprs[5], regs->gprs[6], regs->gprs[7]); - printk(" " FOURLONG, - regs->gprs[8], regs->gprs[9], regs->gprs[10], regs->gprs[11]); - printk(" " FOURLONG, - regs->gprs[12], regs->gprs[13], regs->gprs[14], regs->gprs[15]); - - show_code(regs); -} - -void show_regs(struct pt_regs *regs) -{ - print_modules(); - printk("CPU: %d %s %s %.*s\n", - task_thread_info(current)->cpu, print_tainted(), - init_utsname()->release, - (int)strcspn(init_utsname()->version, " "), - init_utsname()->version); - printk("Process %s (pid: %d, task: %p, ksp: %p)\n", - current->comm, current->pid, current, - (void *) current->thread.ksp); - show_registers(regs); - /* Show stack backtrace if pt_regs is from kernel mode */ - if (!(regs->psw.mask & PSW_MASK_PSTATE)) - show_trace(NULL, (unsigned long *) regs->gprs[15]); - show_last_breaking_event(regs); -} - -static DEFINE_SPINLOCK(die_lock); - -void die(struct pt_regs *regs, const char *str) -{ - static int die_counter; - - oops_enter(); - lgr_info_log(); - debug_stop_all(); - console_verbose(); - spin_lock_irq(&die_lock); - bust_spinlocks(1); - printk("%s: %04x [#%d] ", str, regs->int_code & 0xffff, ++die_counter); -#ifdef CONFIG_PREEMPT - printk("PREEMPT "); -#endif -#ifdef CONFIG_SMP - printk("SMP "); -#endif -#ifdef CONFIG_DEBUG_PAGEALLOC - printk("DEBUG_PAGEALLOC"); -#endif - printk("\n"); - notify_die(DIE_OOPS, str, regs, 0, regs->int_code & 0xffff, SIGSEGV); - show_regs(regs); - bust_spinlocks(0); - add_taint(TAINT_DIE); - spin_unlock_irq(&die_lock); - if (in_interrupt()) - panic("Fatal exception in interrupt"); - if (panic_on_oops) - panic("Fatal exception: panic_on_oops"); - oops_exit(); - do_exit(SIGSEGV); -} - -static inline void report_user_fault(struct pt_regs *regs, int signr) -{ - if ((task_pid_nr(current) > 1) && !show_unhandled_signals) - return; - if (!unhandled_signal(current, signr)) - return; - if (!printk_ratelimit()) - return; - printk("User process fault: interruption code 0x%X ", regs->int_code); - print_vma_addr("in ", regs->psw.addr & PSW_ADDR_INSN); - printk("\n"); - show_regs(regs); -} - -int is_valid_bugaddr(unsigned long addr) -{ - return 1; -} - -static inline void __user *get_psw_address(struct pt_regs *regs) -{ - return (void __user *) - ((regs->psw.addr - (regs->int_code >> 16)) & PSW_ADDR_INSN); -} - -static void __kprobes do_trap(struct pt_regs *regs, - int si_signo, int si_code, char *str) -{ - siginfo_t info; - - if (notify_die(DIE_TRAP, str, regs, 0, - regs->int_code, si_signo) == NOTIFY_STOP) - return; - - if (regs->psw.mask & PSW_MASK_PSTATE) { - info.si_signo = si_signo; - info.si_errno = 0; - info.si_code = si_code; - info.si_addr = get_psw_address(regs); - force_sig_info(si_signo, &info, current); - report_user_fault(regs, si_signo); - } else { - const struct exception_table_entry *fixup; - fixup = search_exception_tables(regs->psw.addr & PSW_ADDR_INSN); - if (fixup) - regs->psw.addr = fixup->fixup | PSW_ADDR_AMODE; - else { - enum bug_trap_type btt; - - btt = report_bug(regs->psw.addr & PSW_ADDR_INSN, regs); - if (btt == BUG_TRAP_TYPE_WARN) - return; - die(regs, str); - } - } -} - -void __kprobes do_per_trap(struct pt_regs *regs) -{ - siginfo_t info; - - if (notify_die(DIE_SSTEP, "sstep", regs, 0, 0, SIGTRAP) == NOTIFY_STOP) - return; - if (!current->ptrace) - return; - info.si_signo = SIGTRAP; - info.si_errno = 0; - info.si_code = TRAP_HWBKPT; - info.si_addr = - (void __force __user *) current->thread.per_event.address; - force_sig_info(SIGTRAP, &info, current); -} - -static void default_trap_handler(struct pt_regs *regs) -{ - if (regs->psw.mask & PSW_MASK_PSTATE) { - report_user_fault(regs, SIGSEGV); - do_exit(SIGSEGV); - } else - die(regs, "Unknown program exception"); -} - -#define DO_ERROR_INFO(name, signr, sicode, str) \ -static void name(struct pt_regs *regs) \ -{ \ - do_trap(regs, signr, sicode, str); \ -} - -DO_ERROR_INFO(addressing_exception, SIGILL, ILL_ILLADR, - "addressing exception") -DO_ERROR_INFO(execute_exception, SIGILL, ILL_ILLOPN, - "execute exception") -DO_ERROR_INFO(divide_exception, SIGFPE, FPE_INTDIV, - "fixpoint divide exception") -DO_ERROR_INFO(overflow_exception, SIGFPE, FPE_INTOVF, - "fixpoint overflow exception") -DO_ERROR_INFO(hfp_overflow_exception, SIGFPE, FPE_FLTOVF, - "HFP overflow exception") -DO_ERROR_INFO(hfp_underflow_exception, SIGFPE, FPE_FLTUND, - "HFP underflow exception") -DO_ERROR_INFO(hfp_significance_exception, SIGFPE, FPE_FLTRES, - "HFP significance exception") -DO_ERROR_INFO(hfp_divide_exception, SIGFPE, FPE_FLTDIV, - "HFP divide exception") -DO_ERROR_INFO(hfp_sqrt_exception, SIGFPE, FPE_FLTINV, - "HFP square root exception") -DO_ERROR_INFO(operand_exception, SIGILL, ILL_ILLOPN, - "operand exception") -DO_ERROR_INFO(privileged_op, SIGILL, ILL_PRVOPC, - "privileged operation") -DO_ERROR_INFO(special_op_exception, SIGILL, ILL_ILLOPN, - "special operation exception") -DO_ERROR_INFO(translation_exception, SIGILL, ILL_ILLOPN, - "translation exception") - -static inline void do_fp_trap(struct pt_regs *regs, int fpc) -{ - int si_code = 0; - /* FPC[2] is Data Exception Code */ - if ((fpc & 0x00000300) == 0) { - /* bits 6 and 7 of DXC are 0 iff IEEE exception */ - if (fpc & 0x8000) /* invalid fp operation */ - si_code = FPE_FLTINV; - else if (fpc & 0x4000) /* div by 0 */ - si_code = FPE_FLTDIV; - else if (fpc & 0x2000) /* overflow */ - si_code = FPE_FLTOVF; - else if (fpc & 0x1000) /* underflow */ - si_code = FPE_FLTUND; - else if (fpc & 0x0800) /* inexact */ - si_code = FPE_FLTRES; - } - do_trap(regs, SIGFPE, si_code, "floating point exception"); -} - -static void __kprobes illegal_op(struct pt_regs *regs) -{ - siginfo_t info; - __u8 opcode[6]; - __u16 __user *location; - int signal = 0; - - location = get_psw_address(regs); - - if (regs->psw.mask & PSW_MASK_PSTATE) { - if (get_user(*((__u16 *) opcode), (__u16 __user *) location)) - return; - if (*((__u16 *) opcode) == S390_BREAKPOINT_U16) { - if (current->ptrace) { - info.si_signo = SIGTRAP; - info.si_errno = 0; - info.si_code = TRAP_BRKPT; - info.si_addr = location; - force_sig_info(SIGTRAP, &info, current); - } else - signal = SIGILL; -#ifdef CONFIG_MATHEMU - } else if (opcode[0] == 0xb3) { - if (get_user(*((__u16 *) (opcode+2)), location+1)) - return; - signal = math_emu_b3(opcode, regs); - } else if (opcode[0] == 0xed) { - if (get_user(*((__u32 *) (opcode+2)), - (__u32 __user *)(location+1))) - return; - signal = math_emu_ed(opcode, regs); - } else if (*((__u16 *) opcode) == 0xb299) { - if (get_user(*((__u16 *) (opcode+2)), location+1)) - return; - signal = math_emu_srnm(opcode, regs); - } else if (*((__u16 *) opcode) == 0xb29c) { - if (get_user(*((__u16 *) (opcode+2)), location+1)) - return; - signal = math_emu_stfpc(opcode, regs); - } else if (*((__u16 *) opcode) == 0xb29d) { - if (get_user(*((__u16 *) (opcode+2)), location+1)) - return; - signal = math_emu_lfpc(opcode, regs); -#endif - } else - signal = SIGILL; - } else { - /* - * If we get an illegal op in kernel mode, send it through the - * kprobes notifier. If kprobes doesn't pick it up, SIGILL - */ - if (notify_die(DIE_BPT, "bpt", regs, 0, - 3, SIGTRAP) != NOTIFY_STOP) - signal = SIGILL; - } - -#ifdef CONFIG_MATHEMU - if (signal == SIGFPE) - do_fp_trap(regs, current->thread.fp_regs.fpc); - else if (signal == SIGSEGV) - do_trap(regs, signal, SEGV_MAPERR, "user address fault"); - else -#endif - if (signal) - do_trap(regs, signal, ILL_ILLOPC, "illegal operation"); -} - - -#ifdef CONFIG_MATHEMU -void specification_exception(struct pt_regs *regs) -{ - __u8 opcode[6]; - __u16 __user *location = NULL; - int signal = 0; - - location = (__u16 __user *) get_psw_address(regs); - - if (regs->psw.mask & PSW_MASK_PSTATE) { - get_user(*((__u16 *) opcode), location); - switch (opcode[0]) { - case 0x28: /* LDR Rx,Ry */ - signal = math_emu_ldr(opcode); - break; - case 0x38: /* LER Rx,Ry */ - signal = math_emu_ler(opcode); - break; - case 0x60: /* STD R,D(X,B) */ - get_user(*((__u16 *) (opcode+2)), location+1); - signal = math_emu_std(opcode, regs); - break; - case 0x68: /* LD R,D(X,B) */ - get_user(*((__u16 *) (opcode+2)), location+1); - signal = math_emu_ld(opcode, regs); - break; - case 0x70: /* STE R,D(X,B) */ - get_user(*((__u16 *) (opcode+2)), location+1); - signal = math_emu_ste(opcode, regs); - break; - case 0x78: /* LE R,D(X,B) */ - get_user(*((__u16 *) (opcode+2)), location+1); - signal = math_emu_le(opcode, regs); - break; - default: - signal = SIGILL; - break; - } - } else - signal = SIGILL; - - if (signal == SIGFPE) - do_fp_trap(regs, current->thread.fp_regs.fpc); - else if (signal) - do_trap(regs, signal, ILL_ILLOPN, "specification exception"); -} -#else -DO_ERROR_INFO(specification_exception, SIGILL, ILL_ILLOPN, - "specification exception"); -#endif - -static void data_exception(struct pt_regs *regs) -{ - __u16 __user *location; - int signal = 0; - - location = get_psw_address(regs); - - if (MACHINE_HAS_IEEE) - asm volatile("stfpc %0" : "=m" (current->thread.fp_regs.fpc)); - -#ifdef CONFIG_MATHEMU - else if (regs->psw.mask & PSW_MASK_PSTATE) { - __u8 opcode[6]; - get_user(*((__u16 *) opcode), location); - switch (opcode[0]) { - case 0x28: /* LDR Rx,Ry */ - signal = math_emu_ldr(opcode); - break; - case 0x38: /* LER Rx,Ry */ - signal = math_emu_ler(opcode); - break; - case 0x60: /* STD R,D(X,B) */ - get_user(*((__u16 *) (opcode+2)), location+1); - signal = math_emu_std(opcode, regs); - break; - case 0x68: /* LD R,D(X,B) */ - get_user(*((__u16 *) (opcode+2)), location+1); - signal = math_emu_ld(opcode, regs); - break; - case 0x70: /* STE R,D(X,B) */ - get_user(*((__u16 *) (opcode+2)), location+1); - signal = math_emu_ste(opcode, regs); - break; - case 0x78: /* LE R,D(X,B) */ - get_user(*((__u16 *) (opcode+2)), location+1); - signal = math_emu_le(opcode, regs); - break; - case 0xb3: - get_user(*((__u16 *) (opcode+2)), location+1); - signal = math_emu_b3(opcode, regs); - break; - case 0xed: - get_user(*((__u32 *) (opcode+2)), - (__u32 __user *)(location+1)); - signal = math_emu_ed(opcode, regs); - break; - case 0xb2: - if (opcode[1] == 0x99) { - get_user(*((__u16 *) (opcode+2)), location+1); - signal = math_emu_srnm(opcode, regs); - } else if (opcode[1] == 0x9c) { - get_user(*((__u16 *) (opcode+2)), location+1); - signal = math_emu_stfpc(opcode, regs); - } else if (opcode[1] == 0x9d) { - get_user(*((__u16 *) (opcode+2)), location+1); - signal = math_emu_lfpc(opcode, regs); - } else - signal = SIGILL; - break; - default: - signal = SIGILL; - break; - } - } -#endif - if (current->thread.fp_regs.fpc & FPC_DXC_MASK) - signal = SIGFPE; - else - signal = SIGILL; - if (signal == SIGFPE) - do_fp_trap(regs, current->thread.fp_regs.fpc); - else if (signal) - do_trap(regs, signal, ILL_ILLOPN, "data exception"); -} - -static void space_switch_exception(struct pt_regs *regs) -{ - /* Set user psw back to home space mode. */ - if (regs->psw.mask & PSW_MASK_PSTATE) - regs->psw.mask |= PSW_ASC_HOME; - /* Send SIGILL. */ - do_trap(regs, SIGILL, ILL_PRVOPC, "space switch event"); -} - -void __kprobes kernel_stack_overflow(struct pt_regs * regs) -{ - bust_spinlocks(1); - printk("Kernel stack overflow.\n"); - show_regs(regs); - bust_spinlocks(0); - panic("Corrupt kernel stack, can't continue."); -} - -/* init is done in lowcore.S and head.S */ - -void __init trap_init(void) -{ - int i; - - for (i = 0; i < 128; i++) - pgm_check_table[i] = &default_trap_handler; - pgm_check_table[1] = &illegal_op; - pgm_check_table[2] = &privileged_op; - pgm_check_table[3] = &execute_exception; - pgm_check_table[4] = &do_protection_exception; - pgm_check_table[5] = &addressing_exception; - pgm_check_table[6] = &specification_exception; - pgm_check_table[7] = &data_exception; - pgm_check_table[8] = &overflow_exception; - pgm_check_table[9] = ÷_exception; - pgm_check_table[0x0A] = &overflow_exception; - pgm_check_table[0x0B] = ÷_exception; - pgm_check_table[0x0C] = &hfp_overflow_exception; - pgm_check_table[0x0D] = &hfp_underflow_exception; - pgm_check_table[0x0E] = &hfp_significance_exception; - pgm_check_table[0x0F] = &hfp_divide_exception; - pgm_check_table[0x10] = &do_dat_exception; - pgm_check_table[0x11] = &do_dat_exception; - pgm_check_table[0x12] = &translation_exception; - pgm_check_table[0x13] = &special_op_exception; -#ifdef CONFIG_64BIT - pgm_check_table[0x38] = &do_asce_exception; - pgm_check_table[0x39] = &do_dat_exception; - pgm_check_table[0x3A] = &do_dat_exception; - pgm_check_table[0x3B] = &do_dat_exception; -#endif /* CONFIG_64BIT */ - pgm_check_table[0x15] = &operand_exception; - pgm_check_table[0x1C] = &space_switch_exception; - pgm_check_table[0x1D] = &hfp_sqrt_exception; - /* Enable machine checks early. */ - local_mcck_enable(); -} diff --git a/ANDROID_3.4.5/arch/s390/kernel/vdso.c b/ANDROID_3.4.5/arch/s390/kernel/vdso.c deleted file mode 100644 index ea5590fd..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/vdso.c +++ /dev/null @@ -1,333 +0,0 @@ -/* - * vdso setup for s390 - * - * Copyright IBM Corp. 2008 - * Author(s): Martin Schwidefsky (schwidefsky@de.ibm.com) - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License (version 2 only) - * as published by the Free Software Foundation. - */ - -#include <linux/module.h> -#include <linux/errno.h> -#include <linux/sched.h> -#include <linux/kernel.h> -#include <linux/mm.h> -#include <linux/smp.h> -#include <linux/stddef.h> -#include <linux/unistd.h> -#include <linux/slab.h> -#include <linux/user.h> -#include <linux/elf.h> -#include <linux/security.h> -#include <linux/bootmem.h> -#include <linux/compat.h> -#include <asm/asm-offsets.h> -#include <asm/pgtable.h> -#include <asm/processor.h> -#include <asm/mmu.h> -#include <asm/mmu_context.h> -#include <asm/sections.h> -#include <asm/vdso.h> -#include <asm/facility.h> - -#if defined(CONFIG_32BIT) || defined(CONFIG_COMPAT) -extern char vdso32_start, vdso32_end; -static void *vdso32_kbase = &vdso32_start; -static unsigned int vdso32_pages; -static struct page **vdso32_pagelist; -#endif - -#ifdef CONFIG_64BIT -extern char vdso64_start, vdso64_end; -static void *vdso64_kbase = &vdso64_start; -static unsigned int vdso64_pages; -static struct page **vdso64_pagelist; -#endif /* CONFIG_64BIT */ - -/* - * Should the kernel map a VDSO page into processes and pass its - * address down to glibc upon exec()? - */ -unsigned int __read_mostly vdso_enabled = 1; - -static int __init vdso_setup(char *s) -{ - unsigned long val; - int rc; - - rc = 0; - if (strncmp(s, "on", 3) == 0) - vdso_enabled = 1; - else if (strncmp(s, "off", 4) == 0) - vdso_enabled = 0; - else { - rc = strict_strtoul(s, 0, &val); - vdso_enabled = rc ? 0 : !!val; - } - return !rc; -} -__setup("vdso=", vdso_setup); - -/* - * The vdso data page - */ -static union { - struct vdso_data data; - u8 page[PAGE_SIZE]; -} vdso_data_store __page_aligned_data; -struct vdso_data *vdso_data = &vdso_data_store.data; - -/* - * Setup vdso data page. - */ -static void vdso_init_data(struct vdso_data *vd) -{ - vd->ectg_available = user_mode != HOME_SPACE_MODE && test_facility(31); -} - -#ifdef CONFIG_64BIT -/* - * Allocate/free per cpu vdso data. - */ -#define SEGMENT_ORDER 2 - -int vdso_alloc_per_cpu(struct _lowcore *lowcore) -{ - unsigned long segment_table, page_table, page_frame; - u32 *psal, *aste; - int i; - - lowcore->vdso_per_cpu_data = __LC_PASTE; - - if (user_mode == HOME_SPACE_MODE || !vdso_enabled) - return 0; - - segment_table = __get_free_pages(GFP_KERNEL, SEGMENT_ORDER); - page_table = get_zeroed_page(GFP_KERNEL | GFP_DMA); - page_frame = get_zeroed_page(GFP_KERNEL); - if (!segment_table || !page_table || !page_frame) - goto out; - - clear_table((unsigned long *) segment_table, _SEGMENT_ENTRY_EMPTY, - PAGE_SIZE << SEGMENT_ORDER); - clear_table((unsigned long *) page_table, _PAGE_TYPE_EMPTY, - 256*sizeof(unsigned long)); - - *(unsigned long *) segment_table = _SEGMENT_ENTRY + page_table; - *(unsigned long *) page_table = _PAGE_RO + page_frame; - - psal = (u32 *) (page_table + 256*sizeof(unsigned long)); - aste = psal + 32; - - for (i = 4; i < 32; i += 4) - psal[i] = 0x80000000; - - lowcore->paste[4] = (u32)(addr_t) psal; - psal[0] = 0x20000000; - psal[2] = (u32)(addr_t) aste; - *(unsigned long *) (aste + 2) = segment_table + - _ASCE_TABLE_LENGTH + _ASCE_USER_BITS + _ASCE_TYPE_SEGMENT; - aste[4] = (u32)(addr_t) psal; - lowcore->vdso_per_cpu_data = page_frame; - - return 0; - -out: - free_page(page_frame); - free_page(page_table); - free_pages(segment_table, SEGMENT_ORDER); - return -ENOMEM; -} - -void vdso_free_per_cpu(struct _lowcore *lowcore) -{ - unsigned long segment_table, page_table, page_frame; - u32 *psal, *aste; - - if (user_mode == HOME_SPACE_MODE || !vdso_enabled) - return; - - psal = (u32 *)(addr_t) lowcore->paste[4]; - aste = (u32 *)(addr_t) psal[2]; - segment_table = *(unsigned long *)(aste + 2) & PAGE_MASK; - page_table = *(unsigned long *) segment_table; - page_frame = *(unsigned long *) page_table; - - free_page(page_frame); - free_page(page_table); - free_pages(segment_table, SEGMENT_ORDER); -} - -static void vdso_init_cr5(void) -{ - unsigned long cr5; - - if (user_mode == HOME_SPACE_MODE || !vdso_enabled) - return; - cr5 = offsetof(struct _lowcore, paste); - __ctl_load(cr5, 5, 5); -} -#endif /* CONFIG_64BIT */ - -/* - * This is called from binfmt_elf, we create the special vma for the - * vDSO and insert it into the mm struct tree - */ -int arch_setup_additional_pages(struct linux_binprm *bprm, int uses_interp) -{ - struct mm_struct *mm = current->mm; - struct page **vdso_pagelist; - unsigned long vdso_pages; - unsigned long vdso_base; - int rc; - - if (!vdso_enabled) - return 0; - /* - * Only map the vdso for dynamically linked elf binaries. - */ - if (!uses_interp) - return 0; - -#ifdef CONFIG_64BIT - vdso_pagelist = vdso64_pagelist; - vdso_pages = vdso64_pages; -#ifdef CONFIG_COMPAT - if (is_compat_task()) { - vdso_pagelist = vdso32_pagelist; - vdso_pages = vdso32_pages; - } -#endif -#else - vdso_pagelist = vdso32_pagelist; - vdso_pages = vdso32_pages; -#endif - - /* - * vDSO has a problem and was disabled, just don't "enable" it for - * the process - */ - if (vdso_pages == 0) - return 0; - - current->mm->context.vdso_base = 0; - - /* - * pick a base address for the vDSO in process space. We try to put - * it at vdso_base which is the "natural" base for it, but we might - * fail and end up putting it elsewhere. - */ - down_write(&mm->mmap_sem); - vdso_base = get_unmapped_area(NULL, 0, vdso_pages << PAGE_SHIFT, 0, 0); - if (IS_ERR_VALUE(vdso_base)) { - rc = vdso_base; - goto out_up; - } - - /* - * Put vDSO base into mm struct. We need to do this before calling - * install_special_mapping or the perf counter mmap tracking code - * will fail to recognise it as a vDSO (since arch_vma_name fails). - */ - current->mm->context.vdso_base = vdso_base; - - /* - * our vma flags don't have VM_WRITE so by default, the process - * isn't allowed to write those pages. - * gdb can break that with ptrace interface, and thus trigger COW - * on those pages but it's then your responsibility to never do that - * on the "data" page of the vDSO or you'll stop getting kernel - * updates and your nice userland gettimeofday will be totally dead. - * It's fine to use that for setting breakpoints in the vDSO code - * pages though. - */ - rc = install_special_mapping(mm, vdso_base, vdso_pages << PAGE_SHIFT, - VM_READ|VM_EXEC| - VM_MAYREAD|VM_MAYWRITE|VM_MAYEXEC, - vdso_pagelist); - if (rc) - current->mm->context.vdso_base = 0; -out_up: - up_write(&mm->mmap_sem); - return rc; -} - -const char *arch_vma_name(struct vm_area_struct *vma) -{ - if (vma->vm_mm && vma->vm_start == vma->vm_mm->context.vdso_base) - return "[vdso]"; - return NULL; -} - -static int __init vdso_init(void) -{ - int i; - - if (!vdso_enabled) - return 0; - vdso_init_data(vdso_data); -#if defined(CONFIG_32BIT) || defined(CONFIG_COMPAT) - /* Calculate the size of the 32 bit vDSO */ - vdso32_pages = ((&vdso32_end - &vdso32_start - + PAGE_SIZE - 1) >> PAGE_SHIFT) + 1; - - /* Make sure pages are in the correct state */ - vdso32_pagelist = kzalloc(sizeof(struct page *) * (vdso32_pages + 1), - GFP_KERNEL); - BUG_ON(vdso32_pagelist == NULL); - for (i = 0; i < vdso32_pages - 1; i++) { - struct page *pg = virt_to_page(vdso32_kbase + i*PAGE_SIZE); - ClearPageReserved(pg); - get_page(pg); - vdso32_pagelist[i] = pg; - } - vdso32_pagelist[vdso32_pages - 1] = virt_to_page(vdso_data); - vdso32_pagelist[vdso32_pages] = NULL; -#endif - -#ifdef CONFIG_64BIT - /* Calculate the size of the 64 bit vDSO */ - vdso64_pages = ((&vdso64_end - &vdso64_start - + PAGE_SIZE - 1) >> PAGE_SHIFT) + 1; - - /* Make sure pages are in the correct state */ - vdso64_pagelist = kzalloc(sizeof(struct page *) * (vdso64_pages + 1), - GFP_KERNEL); - BUG_ON(vdso64_pagelist == NULL); - for (i = 0; i < vdso64_pages - 1; i++) { - struct page *pg = virt_to_page(vdso64_kbase + i*PAGE_SIZE); - ClearPageReserved(pg); - get_page(pg); - vdso64_pagelist[i] = pg; - } - vdso64_pagelist[vdso64_pages - 1] = virt_to_page(vdso_data); - vdso64_pagelist[vdso64_pages] = NULL; - if (vdso_alloc_per_cpu(&S390_lowcore)) - BUG(); - vdso_init_cr5(); -#endif /* CONFIG_64BIT */ - - get_page(virt_to_page(vdso_data)); - - smp_wmb(); - - return 0; -} -early_initcall(vdso_init); - -int in_gate_area_no_mm(unsigned long addr) -{ - return 0; -} - -int in_gate_area(struct mm_struct *mm, unsigned long addr) -{ - return 0; -} - -struct vm_area_struct *get_gate_vma(struct mm_struct *mm) -{ - return NULL; -} diff --git a/ANDROID_3.4.5/arch/s390/kernel/vdso32/Makefile b/ANDROID_3.4.5/arch/s390/kernel/vdso32/Makefile deleted file mode 100644 index 8ad2b34a..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/vdso32/Makefile +++ /dev/null @@ -1,58 +0,0 @@ -# List of files in the vdso, has to be asm only for now - -obj-vdso32 = gettimeofday.o clock_getres.o clock_gettime.o note.o - -# Build rules - -targets := $(obj-vdso32) vdso32.so vdso32.so.dbg -obj-vdso32 := $(addprefix $(obj)/, $(obj-vdso32)) - -KBUILD_AFLAGS_31 := $(filter-out -m64,$(KBUILD_AFLAGS)) -KBUILD_AFLAGS_31 += -m31 -s - -KBUILD_CFLAGS_31 := $(filter-out -m64,$(KBUILD_CFLAGS)) -KBUILD_CFLAGS_31 += -m31 -fPIC -shared -fno-common -fno-builtin -KBUILD_CFLAGS_31 += -nostdlib -Wl,-soname=linux-vdso32.so.1 \ - $(call cc-ldoption, -Wl$(comma)--hash-style=sysv) - -$(targets:%=$(obj)/%.dbg): KBUILD_CFLAGS = $(KBUILD_CFLAGS_31) -$(targets:%=$(obj)/%.dbg): KBUILD_AFLAGS = $(KBUILD_AFLAGS_31) - -obj-y += vdso32_wrapper.o -extra-y += vdso32.lds -CPPFLAGS_vdso32.lds += -P -C -U$(ARCH) - -# Disable gcov profiling for VDSO code -GCOV_PROFILE := n - -# Force dependency (incbin is bad) -$(obj)/vdso32_wrapper.o : $(obj)/vdso32.so - -# link rule for the .so file, .lds has to be first -$(obj)/vdso32.so.dbg: $(src)/vdso32.lds $(obj-vdso32) - $(call if_changed,vdso32ld) - -# strip rule for the .so file -$(obj)/%.so: OBJCOPYFLAGS := -S -$(obj)/%.so: $(obj)/%.so.dbg FORCE - $(call if_changed,objcopy) - -# assembly rules for the .S files -$(obj-vdso32): %.o: %.S - $(call if_changed_dep,vdso32as) - -# actual build commands -quiet_cmd_vdso32ld = VDSO32L $@ - cmd_vdso32ld = $(CC) $(c_flags) -Wl,-T $^ -o $@ -quiet_cmd_vdso32as = VDSO32A $@ - cmd_vdso32as = $(CC) $(a_flags) -c -o $@ $< - -# install commands for the unstripped file -quiet_cmd_vdso_install = INSTALL $@ - cmd_vdso_install = cp $(obj)/$@.dbg $(MODLIB)/vdso/$@ - -vdso32.so: $(obj)/vdso32.so.dbg - @mkdir -p $(MODLIB)/vdso - $(call cmd,vdso_install) - -vdso_install: vdso32.so diff --git a/ANDROID_3.4.5/arch/s390/kernel/vdso32/clock_getres.S b/ANDROID_3.4.5/arch/s390/kernel/vdso32/clock_getres.S deleted file mode 100644 index 36aaa25d..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/vdso32/clock_getres.S +++ /dev/null @@ -1,39 +0,0 @@ -/* - * Userland implementation of clock_getres() for 32 bits processes in a - * s390 kernel for use in the vDSO - * - * Copyright IBM Corp. 2008 - * Author(s): Martin Schwidefsky (schwidefsky@de.ibm.com) - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License (version 2 only) - * as published by the Free Software Foundation. - */ -#include <asm/vdso.h> -#include <asm/asm-offsets.h> -#include <asm/unistd.h> - - .text - .align 4 - .globl __kernel_clock_getres - .type __kernel_clock_getres,@function -__kernel_clock_getres: - .cfi_startproc - chi %r2,__CLOCK_REALTIME - je 0f - chi %r2,__CLOCK_MONOTONIC - jne 3f -0: ltr %r3,%r3 - jz 2f /* res == NULL */ - basr %r1,0 -1: l %r0,4f-1b(%r1) - xc 0(4,%r3),0(%r3) /* set tp->tv_sec to zero */ - st %r0,4(%r3) /* store tp->tv_usec */ -2: lhi %r2,0 - br %r14 -3: lhi %r1,__NR_clock_getres /* fallback to svc */ - svc 0 - br %r14 -4: .long __CLOCK_REALTIME_RES - .cfi_endproc - .size __kernel_clock_getres,.-__kernel_clock_getres diff --git a/ANDROID_3.4.5/arch/s390/kernel/vdso32/clock_gettime.S b/ANDROID_3.4.5/arch/s390/kernel/vdso32/clock_gettime.S deleted file mode 100644 index b2224e0b..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/vdso32/clock_gettime.S +++ /dev/null @@ -1,128 +0,0 @@ -/* - * Userland implementation of clock_gettime() for 32 bits processes in a - * s390 kernel for use in the vDSO - * - * Copyright IBM Corp. 2008 - * Author(s): Martin Schwidefsky (schwidefsky@de.ibm.com) - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License (version 2 only) - * as published by the Free Software Foundation. - */ -#include <asm/vdso.h> -#include <asm/asm-offsets.h> -#include <asm/unistd.h> - - .text - .align 4 - .globl __kernel_clock_gettime - .type __kernel_clock_gettime,@function -__kernel_clock_gettime: - .cfi_startproc - basr %r5,0 -0: al %r5,21f-0b(%r5) /* get &_vdso_data */ - chi %r2,__CLOCK_REALTIME - je 10f - chi %r2,__CLOCK_MONOTONIC - jne 19f - - /* CLOCK_MONOTONIC */ - ltr %r3,%r3 - jz 9f /* tp == NULL */ -1: l %r4,__VDSO_UPD_COUNT+4(%r5) /* load update counter */ - tml %r4,0x0001 /* pending update ? loop */ - jnz 1b - stck 24(%r15) /* Store TOD clock */ - lm %r0,%r1,24(%r15) - s %r0,__VDSO_XTIME_STAMP(%r5) /* TOD - cycle_last */ - sl %r1,__VDSO_XTIME_STAMP+4(%r5) - brc 3,2f - ahi %r0,-1 -2: ms %r0,__VDSO_NTP_MULT(%r5) /* cyc2ns(clock,cycle_delta) */ - lr %r2,%r0 - l %r0,__VDSO_NTP_MULT(%r5) - ltr %r1,%r1 - mr %r0,%r0 - jnm 3f - a %r0,__VDSO_NTP_MULT(%r5) -3: alr %r0,%r2 - srdl %r0,12 - al %r0,__VDSO_XTIME_NSEC(%r5) /* + xtime */ - al %r1,__VDSO_XTIME_NSEC+4(%r5) - brc 12,4f - ahi %r0,1 -4: l %r2,__VDSO_XTIME_SEC+4(%r5) - al %r0,__VDSO_WTOM_NSEC(%r5) /* + wall_to_monotonic */ - al %r1,__VDSO_WTOM_NSEC+4(%r5) - brc 12,5f - ahi %r0,1 -5: al %r2,__VDSO_WTOM_SEC+4(%r5) - cl %r4,__VDSO_UPD_COUNT+4(%r5) /* check update counter */ - jne 1b - basr %r5,0 -6: ltr %r0,%r0 - jnz 7f - cl %r1,20f-6b(%r5) - jl 8f -7: ahi %r2,1 - sl %r1,20f-6b(%r5) - brc 3,6b - ahi %r0,-1 - j 6b -8: st %r2,0(%r3) /* store tp->tv_sec */ - st %r1,4(%r3) /* store tp->tv_nsec */ -9: lhi %r2,0 - br %r14 - - /* CLOCK_REALTIME */ -10: ltr %r3,%r3 /* tp == NULL */ - jz 18f -11: l %r4,__VDSO_UPD_COUNT+4(%r5) /* load update counter */ - tml %r4,0x0001 /* pending update ? loop */ - jnz 11b - stck 24(%r15) /* Store TOD clock */ - lm %r0,%r1,24(%r15) - s %r0,__VDSO_XTIME_STAMP(%r5) /* TOD - cycle_last */ - sl %r1,__VDSO_XTIME_STAMP+4(%r5) - brc 3,12f - ahi %r0,-1 -12: ms %r0,__VDSO_NTP_MULT(%r5) /* cyc2ns(clock,cycle_delta) */ - lr %r2,%r0 - l %r0,__VDSO_NTP_MULT(%r5) - ltr %r1,%r1 - mr %r0,%r0 - jnm 13f - a %r0,__VDSO_NTP_MULT(%r5) -13: alr %r0,%r2 - srdl %r0,12 - al %r0,__VDSO_XTIME_NSEC(%r5) /* + xtime */ - al %r1,__VDSO_XTIME_NSEC+4(%r5) - brc 12,14f - ahi %r0,1 -14: l %r2,__VDSO_XTIME_SEC+4(%r5) - cl %r4,__VDSO_UPD_COUNT+4(%r5) /* check update counter */ - jne 11b - basr %r5,0 -15: ltr %r0,%r0 - jnz 16f - cl %r1,20f-15b(%r5) - jl 17f -16: ahi %r2,1 - sl %r1,20f-15b(%r5) - brc 3,15b - ahi %r0,-1 - j 15b -17: st %r2,0(%r3) /* store tp->tv_sec */ - st %r1,4(%r3) /* store tp->tv_nsec */ -18: lhi %r2,0 - br %r14 - - /* Fallback to system call */ -19: lhi %r1,__NR_clock_gettime - svc 0 - br %r14 - -20: .long 1000000000 -21: .long _vdso_data - 0b - .cfi_endproc - .size __kernel_clock_gettime,.-__kernel_clock_gettime diff --git a/ANDROID_3.4.5/arch/s390/kernel/vdso32/gettimeofday.S b/ANDROID_3.4.5/arch/s390/kernel/vdso32/gettimeofday.S deleted file mode 100644 index 2d363317..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/vdso32/gettimeofday.S +++ /dev/null @@ -1,78 +0,0 @@ -/* - * Userland implementation of gettimeofday() for 32 bits processes in a - * s390 kernel for use in the vDSO - * - * Copyright IBM Corp. 2008 - * Author(s): Martin Schwidefsky (schwidefsky@de.ibm.com) - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License (version 2 only) - * as published by the Free Software Foundation. - */ -#include <asm/vdso.h> -#include <asm/asm-offsets.h> -#include <asm/unistd.h> - - .text - .align 4 - .globl __kernel_gettimeofday - .type __kernel_gettimeofday,@function -__kernel_gettimeofday: - .cfi_startproc - basr %r5,0 -0: al %r5,13f-0b(%r5) /* get &_vdso_data */ -1: ltr %r3,%r3 /* check if tz is NULL */ - je 2f - mvc 0(8,%r3),__VDSO_TIMEZONE(%r5) -2: ltr %r2,%r2 /* check if tv is NULL */ - je 10f - l %r4,__VDSO_UPD_COUNT+4(%r5) /* load update counter */ - tml %r4,0x0001 /* pending update ? loop */ - jnz 1b - stck 24(%r15) /* Store TOD clock */ - lm %r0,%r1,24(%r15) - s %r0,__VDSO_XTIME_STAMP(%r5) /* TOD - cycle_last */ - sl %r1,__VDSO_XTIME_STAMP+4(%r5) - brc 3,3f - ahi %r0,-1 -3: ms %r0,__VDSO_NTP_MULT(%r5) /* cyc2ns(clock,cycle_delta) */ - st %r0,24(%r15) - l %r0,__VDSO_NTP_MULT(%r5) - ltr %r1,%r1 - mr %r0,%r0 - jnm 4f - a %r0,__VDSO_NTP_MULT(%r5) -4: al %r0,24(%r15) - srdl %r0,12 - al %r0,__VDSO_XTIME_NSEC(%r5) /* + xtime */ - al %r1,__VDSO_XTIME_NSEC+4(%r5) - brc 12,5f - ahi %r0,1 -5: mvc 24(4,%r15),__VDSO_XTIME_SEC+4(%r5) - cl %r4,__VDSO_UPD_COUNT+4(%r5) /* check update counter */ - jne 1b - l %r4,24(%r15) /* get tv_sec from stack */ - basr %r5,0 -6: ltr %r0,%r0 - jnz 7f - cl %r1,11f-6b(%r5) - jl 8f -7: ahi %r4,1 - sl %r1,11f-6b(%r5) - brc 3,6b - ahi %r0,-1 - j 6b -8: st %r4,0(%r2) /* store tv->tv_sec */ - ltr %r1,%r1 - m %r0,12f-6b(%r5) - jnm 9f - al %r0,12f-6b(%r5) -9: srl %r0,6 - st %r0,4(%r2) /* store tv->tv_usec */ -10: slr %r2,%r2 - br %r14 -11: .long 1000000000 -12: .long 274877907 -13: .long _vdso_data - 0b - .cfi_endproc - .size __kernel_gettimeofday,.-__kernel_gettimeofday diff --git a/ANDROID_3.4.5/arch/s390/kernel/vdso32/note.S b/ANDROID_3.4.5/arch/s390/kernel/vdso32/note.S deleted file mode 100644 index 79a071e4..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/vdso32/note.S +++ /dev/null @@ -1,12 +0,0 @@ -/* - * This supplies .note.* sections to go into the PT_NOTE inside the vDSO text. - * Here we can supply some information useful to userland. - */ - -#include <linux/uts.h> -#include <linux/version.h> -#include <linux/elfnote.h> - -ELFNOTE_START(Linux, 0, "a") - .long LINUX_VERSION_CODE -ELFNOTE_END diff --git a/ANDROID_3.4.5/arch/s390/kernel/vdso32/vdso32.lds.S b/ANDROID_3.4.5/arch/s390/kernel/vdso32/vdso32.lds.S deleted file mode 100644 index a8c379fa..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/vdso32/vdso32.lds.S +++ /dev/null @@ -1,138 +0,0 @@ -/* - * This is the infamous ld script for the 32 bits vdso - * library - */ -#include <asm/vdso.h> - -OUTPUT_FORMAT("elf32-s390", "elf32-s390", "elf32-s390") -OUTPUT_ARCH(s390:31-bit) -ENTRY(_start) - -SECTIONS -{ - . = VDSO32_LBASE + SIZEOF_HEADERS; - - .hash : { *(.hash) } :text - .gnu.hash : { *(.gnu.hash) } - .dynsym : { *(.dynsym) } - .dynstr : { *(.dynstr) } - .gnu.version : { *(.gnu.version) } - .gnu.version_d : { *(.gnu.version_d) } - .gnu.version_r : { *(.gnu.version_r) } - - .note : { *(.note.*) } :text :note - - . = ALIGN(16); - .text : { - *(.text .stub .text.* .gnu.linkonce.t.*) - } :text - PROVIDE(__etext = .); - PROVIDE(_etext = .); - PROVIDE(etext = .); - - /* - * Other stuff is appended to the text segment: - */ - .rodata : { *(.rodata .rodata.* .gnu.linkonce.r.*) } - .rodata1 : { *(.rodata1) } - - .dynamic : { *(.dynamic) } :text :dynamic - - .eh_frame_hdr : { *(.eh_frame_hdr) } :text :eh_frame_hdr - .eh_frame : { KEEP (*(.eh_frame)) } :text - .gcc_except_table : { *(.gcc_except_table .gcc_except_table.*) } - - .rela.dyn ALIGN(8) : { *(.rela.dyn) } - .got ALIGN(8) : { *(.got .toc) } - - _end = .; - PROVIDE(end = .); - - /* - * Stabs debugging sections are here too. - */ - .stab 0 : { *(.stab) } - .stabstr 0 : { *(.stabstr) } - .stab.excl 0 : { *(.stab.excl) } - .stab.exclstr 0 : { *(.stab.exclstr) } - .stab.index 0 : { *(.stab.index) } - .stab.indexstr 0 : { *(.stab.indexstr) } - .comment 0 : { *(.comment) } - - /* - * DWARF debug sections. - * Symbols in the DWARF debugging sections are relative to the - * beginning of the section so we begin them at 0. - */ - /* DWARF 1 */ - .debug 0 : { *(.debug) } - .line 0 : { *(.line) } - /* GNU DWARF 1 extensions */ - .debug_srcinfo 0 : { *(.debug_srcinfo) } - .debug_sfnames 0 : { *(.debug_sfnames) } - /* DWARF 1.1 and DWARF 2 */ - .debug_aranges 0 : { *(.debug_aranges) } - .debug_pubnames 0 : { *(.debug_pubnames) } - /* DWARF 2 */ - .debug_info 0 : { *(.debug_info .gnu.linkonce.wi.*) } - .debug_abbrev 0 : { *(.debug_abbrev) } - .debug_line 0 : { *(.debug_line) } - .debug_frame 0 : { *(.debug_frame) } - .debug_str 0 : { *(.debug_str) } - .debug_loc 0 : { *(.debug_loc) } - .debug_macinfo 0 : { *(.debug_macinfo) } - /* SGI/MIPS DWARF 2 extensions */ - .debug_weaknames 0 : { *(.debug_weaknames) } - .debug_funcnames 0 : { *(.debug_funcnames) } - .debug_typenames 0 : { *(.debug_typenames) } - .debug_varnames 0 : { *(.debug_varnames) } - /* DWARF 3 */ - .debug_pubtypes 0 : { *(.debug_pubtypes) } - .debug_ranges 0 : { *(.debug_ranges) } - .gnu.attributes 0 : { KEEP (*(.gnu.attributes)) } - - . = ALIGN(4096); - PROVIDE(_vdso_data = .); - - /DISCARD/ : { - *(.note.GNU-stack) - *(.branch_lt) - *(.data .data.* .gnu.linkonce.d.* .sdata*) - *(.bss .sbss .dynbss .dynsbss) - } -} - -/* - * Very old versions of ld do not recognize this name token; use the constant. - */ -#define PT_GNU_EH_FRAME 0x6474e550 - -/* - * We must supply the ELF program headers explicitly to get just one - * PT_LOAD segment, and set the flags explicitly to make segments read-only. - */ -PHDRS -{ - text PT_LOAD FILEHDR PHDRS FLAGS(5); /* PF_R|PF_X */ - dynamic PT_DYNAMIC FLAGS(4); /* PF_R */ - note PT_NOTE FLAGS(4); /* PF_R */ - eh_frame_hdr PT_GNU_EH_FRAME; -} - -/* - * This controls what symbols we export from the DSO. - */ -VERSION -{ - VDSO_VERSION_STRING { - global: - /* - * Has to be there for the kernel to find - */ - __kernel_gettimeofday; - __kernel_clock_gettime; - __kernel_clock_getres; - - local: *; - }; -} diff --git a/ANDROID_3.4.5/arch/s390/kernel/vdso32/vdso32_wrapper.S b/ANDROID_3.4.5/arch/s390/kernel/vdso32/vdso32_wrapper.S deleted file mode 100644 index ae42f8ce..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/vdso32/vdso32_wrapper.S +++ /dev/null @@ -1,14 +0,0 @@ -#include <linux/init.h> -#include <linux/linkage.h> -#include <asm/page.h> - - __PAGE_ALIGNED_DATA - - .globl vdso32_start, vdso32_end - .balign PAGE_SIZE -vdso32_start: - .incbin "arch/s390/kernel/vdso32/vdso32.so" - .balign PAGE_SIZE -vdso32_end: - - .previous diff --git a/ANDROID_3.4.5/arch/s390/kernel/vdso64/Makefile b/ANDROID_3.4.5/arch/s390/kernel/vdso64/Makefile deleted file mode 100644 index 2a8ddfd1..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/vdso64/Makefile +++ /dev/null @@ -1,58 +0,0 @@ -# List of files in the vdso, has to be asm only for now - -obj-vdso64 = gettimeofday.o clock_getres.o clock_gettime.o note.o - -# Build rules - -targets := $(obj-vdso64) vdso64.so vdso64.so.dbg -obj-vdso64 := $(addprefix $(obj)/, $(obj-vdso64)) - -KBUILD_AFLAGS_64 := $(filter-out -m64,$(KBUILD_AFLAGS)) -KBUILD_AFLAGS_64 += -m64 -s - -KBUILD_CFLAGS_64 := $(filter-out -m64,$(KBUILD_CFLAGS)) -KBUILD_CFLAGS_64 += -m64 -fPIC -shared -fno-common -fno-builtin -KBUILD_CFLAGS_64 += -nostdlib -Wl,-soname=linux-vdso64.so.1 \ - $(call cc-ldoption, -Wl$(comma)--hash-style=sysv) - -$(targets:%=$(obj)/%.dbg): KBUILD_CFLAGS = $(KBUILD_CFLAGS_64) -$(targets:%=$(obj)/%.dbg): KBUILD_AFLAGS = $(KBUILD_AFLAGS_64) - -obj-y += vdso64_wrapper.o -extra-y += vdso64.lds -CPPFLAGS_vdso64.lds += -P -C -U$(ARCH) - -# Disable gcov profiling for VDSO code -GCOV_PROFILE := n - -# Force dependency (incbin is bad) -$(obj)/vdso64_wrapper.o : $(obj)/vdso64.so - -# link rule for the .so file, .lds has to be first -$(obj)/vdso64.so.dbg: $(src)/vdso64.lds $(obj-vdso64) - $(call if_changed,vdso64ld) - -# strip rule for the .so file -$(obj)/%.so: OBJCOPYFLAGS := -S -$(obj)/%.so: $(obj)/%.so.dbg FORCE - $(call if_changed,objcopy) - -# assembly rules for the .S files -$(obj-vdso64): %.o: %.S - $(call if_changed_dep,vdso64as) - -# actual build commands -quiet_cmd_vdso64ld = VDSO64L $@ - cmd_vdso64ld = $(CC) $(c_flags) -Wl,-T $^ -o $@ -quiet_cmd_vdso64as = VDSO64A $@ - cmd_vdso64as = $(CC) $(a_flags) -c -o $@ $< - -# install commands for the unstripped file -quiet_cmd_vdso_install = INSTALL $@ - cmd_vdso_install = cp $(obj)/$@.dbg $(MODLIB)/vdso/$@ - -vdso64.so: $(obj)/vdso64.so.dbg - @mkdir -p $(MODLIB)/vdso - $(call cmd,vdso_install) - -vdso_install: vdso64.so diff --git a/ANDROID_3.4.5/arch/s390/kernel/vdso64/clock_getres.S b/ANDROID_3.4.5/arch/s390/kernel/vdso64/clock_getres.S deleted file mode 100644 index 176e1f75..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/vdso64/clock_getres.S +++ /dev/null @@ -1,44 +0,0 @@ -/* - * Userland implementation of clock_getres() for 64 bits processes in a - * s390 kernel for use in the vDSO - * - * Copyright IBM Corp. 2008 - * Author(s): Martin Schwidefsky (schwidefsky@de.ibm.com) - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License (version 2 only) - * as published by the Free Software Foundation. - */ -#include <asm/vdso.h> -#include <asm/asm-offsets.h> -#include <asm/unistd.h> - - .text - .align 4 - .globl __kernel_clock_getres - .type __kernel_clock_getres,@function -__kernel_clock_getres: - .cfi_startproc - cghi %r2,__CLOCK_REALTIME - je 0f - cghi %r2,__CLOCK_MONOTONIC - je 0f - cghi %r2,-2 /* CLOCK_THREAD_CPUTIME_ID for this thread */ - jne 2f - larl %r5,_vdso_data - icm %r0,15,__LC_ECTG_OK(%r5) - jz 2f -0: ltgr %r3,%r3 - jz 1f /* res == NULL */ - larl %r1,3f - lg %r0,0(%r1) - xc 0(8,%r3),0(%r3) /* set tp->tv_sec to zero */ - stg %r0,8(%r3) /* store tp->tv_usec */ -1: lghi %r2,0 - br %r14 -2: lghi %r1,__NR_clock_getres /* fallback to svc */ - svc 0 - br %r14 -3: .quad __CLOCK_REALTIME_RES - .cfi_endproc - .size __kernel_clock_getres,.-__kernel_clock_getres diff --git a/ANDROID_3.4.5/arch/s390/kernel/vdso64/clock_gettime.S b/ANDROID_3.4.5/arch/s390/kernel/vdso64/clock_gettime.S deleted file mode 100644 index d46c95ed..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/vdso64/clock_gettime.S +++ /dev/null @@ -1,125 +0,0 @@ -/* - * Userland implementation of clock_gettime() for 64 bits processes in a - * s390 kernel for use in the vDSO - * - * Copyright IBM Corp. 2008 - * Author(s): Martin Schwidefsky (schwidefsky@de.ibm.com) - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License (version 2 only) - * as published by the Free Software Foundation. - */ -#include <asm/vdso.h> -#include <asm/asm-offsets.h> -#include <asm/unistd.h> - - .text - .align 4 - .globl __kernel_clock_gettime - .type __kernel_clock_gettime,@function -__kernel_clock_gettime: - .cfi_startproc - larl %r5,_vdso_data - cghi %r2,__CLOCK_REALTIME - je 4f - cghi %r2,-2 /* CLOCK_THREAD_CPUTIME_ID for this thread */ - je 9f - cghi %r2,__CLOCK_MONOTONIC - jne 12f - - /* CLOCK_MONOTONIC */ - ltgr %r3,%r3 - jz 3f /* tp == NULL */ -0: lg %r4,__VDSO_UPD_COUNT(%r5) /* load update counter */ - tmll %r4,0x0001 /* pending update ? loop */ - jnz 0b - stck 48(%r15) /* Store TOD clock */ - lg %r1,48(%r15) - sg %r1,__VDSO_XTIME_STAMP(%r5) /* TOD - cycle_last */ - msgf %r1,__VDSO_NTP_MULT(%r5) /* * NTP adjustment */ - srlg %r1,%r1,12 /* cyc2ns(clock,cycle_delta) */ - alg %r1,__VDSO_XTIME_NSEC(%r5) /* + xtime */ - lg %r0,__VDSO_XTIME_SEC(%r5) - alg %r1,__VDSO_WTOM_NSEC(%r5) /* + wall_to_monotonic */ - alg %r0,__VDSO_WTOM_SEC(%r5) - clg %r4,__VDSO_UPD_COUNT(%r5) /* check update counter */ - jne 0b - larl %r5,13f -1: clg %r1,0(%r5) - jl 2f - slg %r1,0(%r5) - aghi %r0,1 - j 1b -2: stg %r0,0(%r3) /* store tp->tv_sec */ - stg %r1,8(%r3) /* store tp->tv_nsec */ -3: lghi %r2,0 - br %r14 - - /* CLOCK_REALTIME */ -4: ltr %r3,%r3 /* tp == NULL */ - jz 8f -5: lg %r4,__VDSO_UPD_COUNT(%r5) /* load update counter */ - tmll %r4,0x0001 /* pending update ? loop */ - jnz 5b - stck 48(%r15) /* Store TOD clock */ - lg %r1,48(%r15) - sg %r1,__VDSO_XTIME_STAMP(%r5) /* TOD - cycle_last */ - msgf %r1,__VDSO_NTP_MULT(%r5) /* * NTP adjustment */ - srlg %r1,%r1,12 /* cyc2ns(clock,cycle_delta) */ - alg %r1,__VDSO_XTIME_NSEC(%r5) /* + xtime */ - lg %r0,__VDSO_XTIME_SEC(%r5) - clg %r4,__VDSO_UPD_COUNT(%r5) /* check update counter */ - jne 5b - larl %r5,13f -6: clg %r1,0(%r5) - jl 7f - slg %r1,0(%r5) - aghi %r0,1 - j 6b -7: stg %r0,0(%r3) /* store tp->tv_sec */ - stg %r1,8(%r3) /* store tp->tv_nsec */ -8: lghi %r2,0 - br %r14 - - /* CLOCK_THREAD_CPUTIME_ID for this thread */ -9: icm %r0,15,__VDSO_ECTG_OK(%r5) - jz 12f - ear %r2,%a4 - llilh %r4,0x0100 - sar %a4,%r4 - lghi %r4,0 - epsw %r5,0 - sacf 512 /* Magic ectg instruction */ - .insn ssf,0xc80100000000,__VDSO_ECTG_BASE(4),__VDSO_ECTG_USER(4),4 - tml %r5,0x4000 - jo 11f - tml %r5,0x8000 - jno 10f - sacf 256 - j 11f -10: sacf 0 -11: sar %a4,%r2 - algr %r1,%r0 /* r1 = cputime as TOD value */ - mghi %r1,1000 /* convert to nanoseconds */ - srlg %r1,%r1,12 /* r1 = cputime in nanosec */ - lgr %r4,%r1 - larl %r5,13f - srlg %r1,%r1,9 /* divide by 1000000000 */ - mlg %r0,8(%r5) - srlg %r0,%r0,11 /* r0 = tv_sec */ - stg %r0,0(%r3) - msg %r0,0(%r5) /* calculate tv_nsec */ - slgr %r4,%r0 /* r4 = tv_nsec */ - stg %r4,8(%r3) - lghi %r2,0 - br %r14 - - /* Fallback to system call */ -12: lghi %r1,__NR_clock_gettime - svc 0 - br %r14 - -13: .quad 1000000000 -14: .quad 19342813113834067 - .cfi_endproc - .size __kernel_clock_gettime,.-__kernel_clock_gettime diff --git a/ANDROID_3.4.5/arch/s390/kernel/vdso64/gettimeofday.S b/ANDROID_3.4.5/arch/s390/kernel/vdso64/gettimeofday.S deleted file mode 100644 index 36ee6747..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/vdso64/gettimeofday.S +++ /dev/null @@ -1,56 +0,0 @@ -/* - * Userland implementation of gettimeofday() for 64 bits processes in a - * s390 kernel for use in the vDSO - * - * Copyright IBM Corp. 2008 - * Author(s): Martin Schwidefsky (schwidefsky@de.ibm.com) - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License (version 2 only) - * as published by the Free Software Foundation. - */ -#include <asm/vdso.h> -#include <asm/asm-offsets.h> -#include <asm/unistd.h> - - .text - .align 4 - .globl __kernel_gettimeofday - .type __kernel_gettimeofday,@function -__kernel_gettimeofday: - .cfi_startproc - larl %r5,_vdso_data -0: ltgr %r3,%r3 /* check if tz is NULL */ - je 1f - mvc 0(8,%r3),__VDSO_TIMEZONE(%r5) -1: ltgr %r2,%r2 /* check if tv is NULL */ - je 4f - lg %r4,__VDSO_UPD_COUNT(%r5) /* load update counter */ - tmll %r4,0x0001 /* pending update ? loop */ - jnz 0b - stck 48(%r15) /* Store TOD clock */ - lg %r1,48(%r15) - sg %r1,__VDSO_XTIME_STAMP(%r5) /* TOD - cycle_last */ - msgf %r1,__VDSO_NTP_MULT(%r5) /* * NTP adjustment */ - srlg %r1,%r1,12 /* cyc2ns(clock,cycle_delta) */ - alg %r1,__VDSO_XTIME_NSEC(%r5) /* + xtime.tv_nsec */ - lg %r0,__VDSO_XTIME_SEC(%r5) /* xtime.tv_sec */ - clg %r4,__VDSO_UPD_COUNT(%r5) /* check update counter */ - jne 0b - larl %r5,5f -2: clg %r1,0(%r5) - jl 3f - slg %r1,0(%r5) - aghi %r0,1 - j 2b -3: stg %r0,0(%r2) /* store tv->tv_sec */ - slgr %r0,%r0 /* tv_nsec -> tv_usec */ - ml %r0,8(%r5) - srlg %r0,%r0,6 - stg %r0,8(%r2) /* store tv->tv_usec */ -4: lghi %r2,0 - br %r14 -5: .quad 1000000000 - .long 274877907 - .cfi_endproc - .size __kernel_gettimeofday,.-__kernel_gettimeofday diff --git a/ANDROID_3.4.5/arch/s390/kernel/vdso64/note.S b/ANDROID_3.4.5/arch/s390/kernel/vdso64/note.S deleted file mode 100644 index 79a071e4..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/vdso64/note.S +++ /dev/null @@ -1,12 +0,0 @@ -/* - * This supplies .note.* sections to go into the PT_NOTE inside the vDSO text. - * Here we can supply some information useful to userland. - */ - -#include <linux/uts.h> -#include <linux/version.h> -#include <linux/elfnote.h> - -ELFNOTE_START(Linux, 0, "a") - .long LINUX_VERSION_CODE -ELFNOTE_END diff --git a/ANDROID_3.4.5/arch/s390/kernel/vdso64/vdso64.lds.S b/ANDROID_3.4.5/arch/s390/kernel/vdso64/vdso64.lds.S deleted file mode 100644 index 9f5979d1..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/vdso64/vdso64.lds.S +++ /dev/null @@ -1,138 +0,0 @@ -/* - * This is the infamous ld script for the 64 bits vdso - * library - */ -#include <asm/vdso.h> - -OUTPUT_FORMAT("elf64-s390", "elf64-s390", "elf64-s390") -OUTPUT_ARCH(s390:64-bit) -ENTRY(_start) - -SECTIONS -{ - . = VDSO64_LBASE + SIZEOF_HEADERS; - - .hash : { *(.hash) } :text - .gnu.hash : { *(.gnu.hash) } - .dynsym : { *(.dynsym) } - .dynstr : { *(.dynstr) } - .gnu.version : { *(.gnu.version) } - .gnu.version_d : { *(.gnu.version_d) } - .gnu.version_r : { *(.gnu.version_r) } - - .note : { *(.note.*) } :text :note - - . = ALIGN(16); - .text : { - *(.text .stub .text.* .gnu.linkonce.t.*) - } :text - PROVIDE(__etext = .); - PROVIDE(_etext = .); - PROVIDE(etext = .); - - /* - * Other stuff is appended to the text segment: - */ - .rodata : { *(.rodata .rodata.* .gnu.linkonce.r.*) } - .rodata1 : { *(.rodata1) } - - .dynamic : { *(.dynamic) } :text :dynamic - - .eh_frame_hdr : { *(.eh_frame_hdr) } :text :eh_frame_hdr - .eh_frame : { KEEP (*(.eh_frame)) } :text - .gcc_except_table : { *(.gcc_except_table .gcc_except_table.*) } - - .rela.dyn ALIGN(8) : { *(.rela.dyn) } - .got ALIGN(8) : { *(.got .toc) } - - _end = .; - PROVIDE(end = .); - - /* - * Stabs debugging sections are here too. - */ - .stab 0 : { *(.stab) } - .stabstr 0 : { *(.stabstr) } - .stab.excl 0 : { *(.stab.excl) } - .stab.exclstr 0 : { *(.stab.exclstr) } - .stab.index 0 : { *(.stab.index) } - .stab.indexstr 0 : { *(.stab.indexstr) } - .comment 0 : { *(.comment) } - - /* - * DWARF debug sections. - * Symbols in the DWARF debugging sections are relative to the - * beginning of the section so we begin them at 0. - */ - /* DWARF 1 */ - .debug 0 : { *(.debug) } - .line 0 : { *(.line) } - /* GNU DWARF 1 extensions */ - .debug_srcinfo 0 : { *(.debug_srcinfo) } - .debug_sfnames 0 : { *(.debug_sfnames) } - /* DWARF 1.1 and DWARF 2 */ - .debug_aranges 0 : { *(.debug_aranges) } - .debug_pubnames 0 : { *(.debug_pubnames) } - /* DWARF 2 */ - .debug_info 0 : { *(.debug_info .gnu.linkonce.wi.*) } - .debug_abbrev 0 : { *(.debug_abbrev) } - .debug_line 0 : { *(.debug_line) } - .debug_frame 0 : { *(.debug_frame) } - .debug_str 0 : { *(.debug_str) } - .debug_loc 0 : { *(.debug_loc) } - .debug_macinfo 0 : { *(.debug_macinfo) } - /* SGI/MIPS DWARF 2 extensions */ - .debug_weaknames 0 : { *(.debug_weaknames) } - .debug_funcnames 0 : { *(.debug_funcnames) } - .debug_typenames 0 : { *(.debug_typenames) } - .debug_varnames 0 : { *(.debug_varnames) } - /* DWARF 3 */ - .debug_pubtypes 0 : { *(.debug_pubtypes) } - .debug_ranges 0 : { *(.debug_ranges) } - .gnu.attributes 0 : { KEEP (*(.gnu.attributes)) } - - . = ALIGN(4096); - PROVIDE(_vdso_data = .); - - /DISCARD/ : { - *(.note.GNU-stack) - *(.branch_lt) - *(.data .data.* .gnu.linkonce.d.* .sdata*) - *(.bss .sbss .dynbss .dynsbss) - } -} - -/* - * Very old versions of ld do not recognize this name token; use the constant. - */ -#define PT_GNU_EH_FRAME 0x6474e550 - -/* - * We must supply the ELF program headers explicitly to get just one - * PT_LOAD segment, and set the flags explicitly to make segments read-only. - */ -PHDRS -{ - text PT_LOAD FILEHDR PHDRS FLAGS(5); /* PF_R|PF_X */ - dynamic PT_DYNAMIC FLAGS(4); /* PF_R */ - note PT_NOTE FLAGS(4); /* PF_R */ - eh_frame_hdr PT_GNU_EH_FRAME; -} - -/* - * This controls what symbols we export from the DSO. - */ -VERSION -{ - VDSO_VERSION_STRING { - global: - /* - * Has to be there for the kernel to find - */ - __kernel_gettimeofday; - __kernel_clock_gettime; - __kernel_clock_getres; - - local: *; - }; -} diff --git a/ANDROID_3.4.5/arch/s390/kernel/vdso64/vdso64_wrapper.S b/ANDROID_3.4.5/arch/s390/kernel/vdso64/vdso64_wrapper.S deleted file mode 100644 index c245842b..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/vdso64/vdso64_wrapper.S +++ /dev/null @@ -1,14 +0,0 @@ -#include <linux/init.h> -#include <linux/linkage.h> -#include <asm/page.h> - - __PAGE_ALIGNED_DATA - - .globl vdso64_start, vdso64_end - .balign PAGE_SIZE -vdso64_start: - .incbin "arch/s390/kernel/vdso64/vdso64.so" - .balign PAGE_SIZE -vdso64_end: - - .previous diff --git a/ANDROID_3.4.5/arch/s390/kernel/vmlinux.lds.S b/ANDROID_3.4.5/arch/s390/kernel/vmlinux.lds.S deleted file mode 100644 index 21109c63..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/vmlinux.lds.S +++ /dev/null @@ -1,96 +0,0 @@ -/* ld script to make s390 Linux kernel - * Written by Martin Schwidefsky (schwidefsky@de.ibm.com) - */ - -#include <asm/thread_info.h> -#include <asm/page.h> -#include <asm-generic/vmlinux.lds.h> - -#ifndef CONFIG_64BIT -OUTPUT_FORMAT("elf32-s390", "elf32-s390", "elf32-s390") -OUTPUT_ARCH(s390) -ENTRY(startup) -jiffies = jiffies_64 + 4; -#else -OUTPUT_FORMAT("elf64-s390", "elf64-s390", "elf64-s390") -OUTPUT_ARCH(s390:64-bit) -ENTRY(startup) -jiffies = jiffies_64; -#endif - -PHDRS { - text PT_LOAD FLAGS(5); /* R_E */ - data PT_LOAD FLAGS(7); /* RWE */ - note PT_NOTE FLAGS(0); /* ___ */ -} - -SECTIONS -{ - . = 0x00000000; - .text : { - _text = .; /* Text and read-only data */ - HEAD_TEXT - TEXT_TEXT - SCHED_TEXT - LOCK_TEXT - KPROBES_TEXT - IRQENTRY_TEXT - *(.fixup) - *(.gnu.warning) - } :text = 0x0700 - - _etext = .; /* End of text section */ - - NOTES :text :note - - .dummy : { *(.dummy) } :data - - RODATA - -#ifdef CONFIG_SHARED_KERNEL - . = ALIGN(0x100000); /* VM shared segments are 1MB aligned */ -#endif - - . = ALIGN(PAGE_SIZE); - _eshared = .; /* End of shareable data */ - _sdata = .; /* Start of data section */ - - EXCEPTION_TABLE(16) :data - - RW_DATA_SECTION(0x100, PAGE_SIZE, THREAD_SIZE) - - _edata = .; /* End of data section */ - - /* will be freed after init */ - . = ALIGN(PAGE_SIZE); /* Init code and data */ - __init_begin = .; - - INIT_TEXT_SECTION(PAGE_SIZE) - - /* - * .exit.text is discarded at runtime, not link time, - * to deal with references from __bug_table - */ - .exit.text : { - EXIT_TEXT - } - - /* early.c uses stsi, which requires page aligned data. */ - . = ALIGN(PAGE_SIZE); - INIT_DATA_SECTION(0x100) - - PERCPU_SECTION(0x100) - . = ALIGN(PAGE_SIZE); - __init_end = .; /* freed after init ends here */ - - BSS_SECTION(0, 2, 0) - - _end = . ; - - /* Debugging sections. */ - STABS_DEBUG - DWARF_DEBUG - - /* Sections to be discarded */ - DISCARDS -} diff --git a/ANDROID_3.4.5/arch/s390/kernel/vtime.c b/ANDROID_3.4.5/arch/s390/kernel/vtime.c deleted file mode 100644 index 39ebff50..00000000 --- a/ANDROID_3.4.5/arch/s390/kernel/vtime.c +++ /dev/null @@ -1,504 +0,0 @@ -/* - * arch/s390/kernel/vtime.c - * Virtual cpu timer based timer functions. - * - * S390 version - * Copyright (C) 2004 IBM Deutschland Entwicklung GmbH, IBM Corporation - * Author(s): Jan Glauber <jan.glauber@de.ibm.com> - */ - -#include <linux/module.h> -#include <linux/kernel.h> -#include <linux/time.h> -#include <linux/delay.h> -#include <linux/init.h> -#include <linux/smp.h> -#include <linux/types.h> -#include <linux/timex.h> -#include <linux/notifier.h> -#include <linux/kernel_stat.h> -#include <linux/rcupdate.h> -#include <linux/posix-timers.h> -#include <linux/cpu.h> -#include <linux/kprobes.h> - -#include <asm/timer.h> -#include <asm/irq_regs.h> -#include <asm/cputime.h> -#include <asm/irq.h> -#include "entry.h" - -static DEFINE_PER_CPU(struct vtimer_queue, virt_cpu_timer); - -DEFINE_PER_CPU(struct s390_idle_data, s390_idle); - -static inline __u64 get_vtimer(void) -{ - __u64 timer; - - asm volatile("STPT %0" : "=m" (timer)); - return timer; -} - -static inline void set_vtimer(__u64 expires) -{ - __u64 timer; - - asm volatile (" STPT %0\n" /* Store current cpu timer value */ - " SPT %1" /* Set new value immediately afterwards */ - : "=m" (timer) : "m" (expires) ); - S390_lowcore.system_timer += S390_lowcore.last_update_timer - timer; - S390_lowcore.last_update_timer = expires; -} - -/* - * Update process times based on virtual cpu times stored by entry.S - * to the lowcore fields user_timer, system_timer & steal_clock. - */ -static void do_account_vtime(struct task_struct *tsk, int hardirq_offset) -{ - struct thread_info *ti = task_thread_info(tsk); - __u64 timer, clock, user, system, steal; - - timer = S390_lowcore.last_update_timer; - clock = S390_lowcore.last_update_clock; - asm volatile (" STPT %0\n" /* Store current cpu timer value */ - " STCK %1" /* Store current tod clock value */ - : "=m" (S390_lowcore.last_update_timer), - "=m" (S390_lowcore.last_update_clock) ); - S390_lowcore.system_timer += timer - S390_lowcore.last_update_timer; - S390_lowcore.steal_timer += S390_lowcore.last_update_clock - clock; - - user = S390_lowcore.user_timer - ti->user_timer; - S390_lowcore.steal_timer -= user; - ti->user_timer = S390_lowcore.user_timer; - account_user_time(tsk, user, user); - - system = S390_lowcore.system_timer - ti->system_timer; - S390_lowcore.steal_timer -= system; - ti->system_timer = S390_lowcore.system_timer; - account_system_time(tsk, hardirq_offset, system, system); - - steal = S390_lowcore.steal_timer; - if ((s64) steal > 0) { - S390_lowcore.steal_timer = 0; - account_steal_time(steal); - } -} - -void account_vtime(struct task_struct *prev, struct task_struct *next) -{ - struct thread_info *ti; - - do_account_vtime(prev, 0); - ti = task_thread_info(prev); - ti->user_timer = S390_lowcore.user_timer; - ti->system_timer = S390_lowcore.system_timer; - ti = task_thread_info(next); - S390_lowcore.user_timer = ti->user_timer; - S390_lowcore.system_timer = ti->system_timer; -} - -void account_process_tick(struct task_struct *tsk, int user_tick) -{ - do_account_vtime(tsk, HARDIRQ_OFFSET); -} - -/* - * Update process times based on virtual cpu times stored by entry.S - * to the lowcore fields user_timer, system_timer & steal_clock. - */ -void account_system_vtime(struct task_struct *tsk) -{ - struct thread_info *ti = task_thread_info(tsk); - __u64 timer, system; - - timer = S390_lowcore.last_update_timer; - S390_lowcore.last_update_timer = get_vtimer(); - S390_lowcore.system_timer += timer - S390_lowcore.last_update_timer; - - system = S390_lowcore.system_timer - ti->system_timer; - S390_lowcore.steal_timer -= system; - ti->system_timer = S390_lowcore.system_timer; - account_system_time(tsk, 0, system, system); -} -EXPORT_SYMBOL_GPL(account_system_vtime); - -void __kprobes vtime_stop_cpu(void) -{ - struct s390_idle_data *idle = &__get_cpu_var(s390_idle); - struct vtimer_queue *vq = &__get_cpu_var(virt_cpu_timer); - unsigned long long idle_time; - unsigned long psw_mask; - - trace_hardirqs_on(); - /* Don't trace preempt off for idle. */ - stop_critical_timings(); - - /* Wait for external, I/O or machine check interrupt. */ - psw_mask = psw_kernel_bits | PSW_MASK_WAIT | PSW_MASK_DAT | - PSW_MASK_IO | PSW_MASK_EXT | PSW_MASK_MCHECK; - idle->nohz_delay = 0; - - /* Call the assembler magic in entry.S */ - psw_idle(idle, vq, psw_mask, !list_empty(&vq->list)); - - /* Reenable preemption tracer. */ - start_critical_timings(); - - /* Account time spent with enabled wait psw loaded as idle time. */ - idle->sequence++; - smp_wmb(); - idle_time = idle->idle_exit - idle->idle_enter; - idle->idle_time += idle_time; - idle->idle_enter = idle->idle_exit = 0ULL; - idle->idle_count++; - account_idle_time(idle_time); - smp_wmb(); - idle->sequence++; -} - -cputime64_t s390_get_idle_time(int cpu) -{ - struct s390_idle_data *idle = &per_cpu(s390_idle, cpu); - unsigned long long now, idle_enter, idle_exit; - unsigned int sequence; - - do { - now = get_clock(); - sequence = ACCESS_ONCE(idle->sequence); - idle_enter = ACCESS_ONCE(idle->idle_enter); - idle_exit = ACCESS_ONCE(idle->idle_exit); - } while ((sequence & 1) || (idle->sequence != sequence)); - return idle_enter ? ((idle_exit ? : now) - idle_enter) : 0; -} - -/* - * Sorted add to a list. List is linear searched until first bigger - * element is found. - */ -static void list_add_sorted(struct vtimer_list *timer, struct list_head *head) -{ - struct vtimer_list *event; - - list_for_each_entry(event, head, entry) { - if (event->expires > timer->expires) { - list_add_tail(&timer->entry, &event->entry); - return; - } - } - list_add_tail(&timer->entry, head); -} - -/* - * Do the callback functions of expired vtimer events. - * Called from within the interrupt handler. - */ -static void do_callbacks(struct list_head *cb_list) -{ - struct vtimer_queue *vq; - struct vtimer_list *event, *tmp; - - if (list_empty(cb_list)) - return; - - vq = &__get_cpu_var(virt_cpu_timer); - - list_for_each_entry_safe(event, tmp, cb_list, entry) { - list_del_init(&event->entry); - (event->function)(event->data); - if (event->interval) { - /* Recharge interval timer */ - event->expires = event->interval + vq->elapsed; - spin_lock(&vq->lock); - list_add_sorted(event, &vq->list); - spin_unlock(&vq->lock); - } - } -} - -/* - * Handler for the virtual CPU timer. - */ -static void do_cpu_timer_interrupt(struct ext_code ext_code, - unsigned int param32, unsigned long param64) -{ - struct vtimer_queue *vq; - struct vtimer_list *event, *tmp; - struct list_head cb_list; /* the callback queue */ - __u64 elapsed, next; - - kstat_cpu(smp_processor_id()).irqs[EXTINT_TMR]++; - INIT_LIST_HEAD(&cb_list); - vq = &__get_cpu_var(virt_cpu_timer); - - /* walk timer list, fire all expired events */ - spin_lock(&vq->lock); - - elapsed = vq->elapsed + (vq->timer - S390_lowcore.async_enter_timer); - BUG_ON((s64) elapsed < 0); - vq->elapsed = 0; - list_for_each_entry_safe(event, tmp, &vq->list, entry) { - if (event->expires < elapsed) - /* move expired timer to the callback queue */ - list_move_tail(&event->entry, &cb_list); - else - event->expires -= elapsed; - } - spin_unlock(&vq->lock); - - do_callbacks(&cb_list); - - /* next event is first in list */ - next = VTIMER_MAX_SLICE; - spin_lock(&vq->lock); - if (!list_empty(&vq->list)) { - event = list_first_entry(&vq->list, struct vtimer_list, entry); - next = event->expires; - } - spin_unlock(&vq->lock); - /* - * To improve precision add the time spent by the - * interrupt handler to the elapsed time. - * Note: CPU timer counts down and we got an interrupt, - * the current content is negative - */ - elapsed = S390_lowcore.async_enter_timer - get_vtimer(); - set_vtimer(next - elapsed); - vq->timer = next - elapsed; - vq->elapsed = elapsed; -} - -void init_virt_timer(struct vtimer_list *timer) -{ - timer->function = NULL; - INIT_LIST_HEAD(&timer->entry); -} -EXPORT_SYMBOL(init_virt_timer); - -static inline int vtimer_pending(struct vtimer_list *timer) -{ - return (!list_empty(&timer->entry)); -} - -/* - * this function should only run on the specified CPU - */ -static void internal_add_vtimer(struct vtimer_list *timer) -{ - struct vtimer_queue *vq; - unsigned long flags; - __u64 left, expires; - - vq = &per_cpu(virt_cpu_timer, timer->cpu); - spin_lock_irqsave(&vq->lock, flags); - - BUG_ON(timer->cpu != smp_processor_id()); - - if (list_empty(&vq->list)) { - /* First timer on this cpu, just program it. */ - list_add(&timer->entry, &vq->list); - set_vtimer(timer->expires); - vq->timer = timer->expires; - vq->elapsed = 0; - } else { - /* Check progress of old timers. */ - expires = timer->expires; - left = get_vtimer(); - if (likely((s64) expires < (s64) left)) { - /* The new timer expires before the current timer. */ - set_vtimer(expires); - vq->elapsed += vq->timer - left; - vq->timer = expires; - } else { - vq->elapsed += vq->timer - left; - vq->timer = left; - } - /* Insert new timer into per cpu list. */ - timer->expires += vq->elapsed; - list_add_sorted(timer, &vq->list); - } - - spin_unlock_irqrestore(&vq->lock, flags); - /* release CPU acquired in prepare_vtimer or mod_virt_timer() */ - put_cpu(); -} - -static inline void prepare_vtimer(struct vtimer_list *timer) -{ - BUG_ON(!timer->function); - BUG_ON(!timer->expires || timer->expires > VTIMER_MAX_SLICE); - BUG_ON(vtimer_pending(timer)); - timer->cpu = get_cpu(); -} - -/* - * add_virt_timer - add an oneshot virtual CPU timer - */ -void add_virt_timer(void *new) -{ - struct vtimer_list *timer; - - timer = (struct vtimer_list *)new; - prepare_vtimer(timer); - timer->interval = 0; - internal_add_vtimer(timer); -} -EXPORT_SYMBOL(add_virt_timer); - -/* - * add_virt_timer_int - add an interval virtual CPU timer - */ -void add_virt_timer_periodic(void *new) -{ - struct vtimer_list *timer; - - timer = (struct vtimer_list *)new; - prepare_vtimer(timer); - timer->interval = timer->expires; - internal_add_vtimer(timer); -} -EXPORT_SYMBOL(add_virt_timer_periodic); - -static int __mod_vtimer(struct vtimer_list *timer, __u64 expires, int periodic) -{ - struct vtimer_queue *vq; - unsigned long flags; - int cpu; - - BUG_ON(!timer->function); - BUG_ON(!expires || expires > VTIMER_MAX_SLICE); - - if (timer->expires == expires && vtimer_pending(timer)) - return 1; - - cpu = get_cpu(); - vq = &per_cpu(virt_cpu_timer, cpu); - - /* disable interrupts before test if timer is pending */ - spin_lock_irqsave(&vq->lock, flags); - - /* if timer isn't pending add it on the current CPU */ - if (!vtimer_pending(timer)) { - spin_unlock_irqrestore(&vq->lock, flags); - - if (periodic) - timer->interval = expires; - else - timer->interval = 0; - timer->expires = expires; - timer->cpu = cpu; - internal_add_vtimer(timer); - return 0; - } - - /* check if we run on the right CPU */ - BUG_ON(timer->cpu != cpu); - - list_del_init(&timer->entry); - timer->expires = expires; - if (periodic) - timer->interval = expires; - - /* the timer can't expire anymore so we can release the lock */ - spin_unlock_irqrestore(&vq->lock, flags); - internal_add_vtimer(timer); - return 1; -} - -/* - * If we change a pending timer the function must be called on the CPU - * where the timer is running on. - * - * returns whether it has modified a pending timer (1) or not (0) - */ -int mod_virt_timer(struct vtimer_list *timer, __u64 expires) -{ - return __mod_vtimer(timer, expires, 0); -} -EXPORT_SYMBOL(mod_virt_timer); - -/* - * If we change a pending timer the function must be called on the CPU - * where the timer is running on. - * - * returns whether it has modified a pending timer (1) or not (0) - */ -int mod_virt_timer_periodic(struct vtimer_list *timer, __u64 expires) -{ - return __mod_vtimer(timer, expires, 1); -} -EXPORT_SYMBOL(mod_virt_timer_periodic); - -/* - * delete a virtual timer - * - * returns whether the deleted timer was pending (1) or not (0) - */ -int del_virt_timer(struct vtimer_list *timer) -{ - unsigned long flags; - struct vtimer_queue *vq; - - /* check if timer is pending */ - if (!vtimer_pending(timer)) - return 0; - - vq = &per_cpu(virt_cpu_timer, timer->cpu); - spin_lock_irqsave(&vq->lock, flags); - - /* we don't interrupt a running timer, just let it expire! */ - list_del_init(&timer->entry); - - spin_unlock_irqrestore(&vq->lock, flags); - return 1; -} -EXPORT_SYMBOL(del_virt_timer); - -/* - * Start the virtual CPU timer on the current CPU. - */ -void init_cpu_vtimer(void) -{ - struct vtimer_queue *vq; - - /* initialize per cpu vtimer structure */ - vq = &__get_cpu_var(virt_cpu_timer); - INIT_LIST_HEAD(&vq->list); - spin_lock_init(&vq->lock); - - /* enable cpu timer interrupts */ - __ctl_set_bit(0,10); - - /* set initial cpu timer */ - set_vtimer(0x7fffffffffffffffULL); -} - -static int __cpuinit s390_nohz_notify(struct notifier_block *self, - unsigned long action, void *hcpu) -{ - struct s390_idle_data *idle; - long cpu = (long) hcpu; - - idle = &per_cpu(s390_idle, cpu); - switch (action) { - case CPU_DYING: - case CPU_DYING_FROZEN: - idle->nohz_delay = 0; - default: - break; - } - return NOTIFY_OK; -} - -void __init vtime_init(void) -{ - /* request the cpu timer external interrupt */ - if (register_external_interrupt(0x1005, do_cpu_timer_interrupt)) - panic("Couldn't request external interrupt 0x1005"); - - /* Enable cpu timer interrupts on the boot cpu. */ - init_cpu_vtimer(); - cpu_notifier(s390_nohz_notify, 0); -} - |