Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

[S390] irq: external interrupt code passing

The external interrupt handlers have a parameter called ext_int_code.
Besides the name this paramter does not only contain the ext_int_code
but in addition also the "cpu address" (POP) which caused the external
interrupt.
To make the code a bit more obvious pass a struct instead so the called
function can easily distinguish between external interrupt code and
cpu address. The cpu address field however is named "subcode" since
some external interrupt sources do not pass a cpu address but a
different parameter (or none at all).

Signed-off-by: Heiko Carstens <heiko.carstens@de.ibm.com>
Signed-off-by: Martin Schwidefsky <schwidefsky@de.ibm.com>

authored by

Heiko Carstens and committed by
Martin Schwidefsky
fde15c3a 2215011d

+32 -30
+6 -1
arch/s390/include/asm/irq.h
··· 34 34 NR_IRQS, 35 35 }; 36 36 37 - typedef void (*ext_int_handler_t)(unsigned int, unsigned int, unsigned long); 37 + struct ext_code { 38 + unsigned short subcode; 39 + unsigned short code; 40 + }; 41 + 42 + typedef void (*ext_int_handler_t)(struct ext_code, unsigned int, unsigned long); 38 43 39 44 int register_external_interrupt(u16 code, ext_int_handler_t handler); 40 45 int unregister_external_interrupt(u16 code, ext_int_handler_t handler);
+2 -1
arch/s390/kernel/entry.h
··· 35 35 siginfo_t *info, sigset_t *oldset, struct pt_regs *regs); 36 36 void do_notify_resume(struct pt_regs *regs); 37 37 38 - void do_extint(struct pt_regs *regs, unsigned int, unsigned int, unsigned long); 38 + struct ext_code; 39 + void do_extint(struct pt_regs *regs, struct ext_code, unsigned int, unsigned long); 39 40 void do_restart(void); 40 41 void __init startup_init(void); 41 42 void die(struct pt_regs *regs, const char *str);
+5 -7
arch/s390/kernel/irq.c
··· 209 209 } 210 210 EXPORT_SYMBOL(unregister_external_interrupt); 211 211 212 - void __irq_entry do_extint(struct pt_regs *regs, unsigned int ext_int_code, 212 + void __irq_entry do_extint(struct pt_regs *regs, struct ext_code ext_code, 213 213 unsigned int param32, unsigned long param64) 214 214 { 215 215 struct pt_regs *old_regs; 216 - unsigned short code; 217 216 struct ext_int_info *p; 218 217 int index; 219 218 220 - code = (unsigned short) ext_int_code; 221 219 old_regs = set_irq_regs(regs); 222 220 irq_enter(); 223 221 if (S390_lowcore.int_clock >= S390_lowcore.clock_comparator) 224 222 /* Serve timer interrupts first. */ 225 223 clock_comparator_work(); 226 224 kstat_cpu(smp_processor_id()).irqs[EXTERNAL_INTERRUPT]++; 227 - if (code != 0x1004) 225 + if (ext_code.code != 0x1004) 228 226 __get_cpu_var(s390_idle).nohz_delay = 1; 229 227 230 - index = ext_hash(code); 228 + index = ext_hash(ext_code.code); 231 229 rcu_read_lock(); 232 230 list_for_each_entry_rcu(p, &ext_int_hash[index], entry) 233 - if (likely(p->code == code)) 234 - p->handler(ext_int_code, param32, param64); 231 + if (likely(p->code == ext_code.code)) 232 + p->handler(ext_code, param32, param64); 235 233 rcu_read_unlock(); 236 234 irq_exit(); 237 235 set_irq_regs(old_regs);
+2 -2
arch/s390/kernel/smp.c
··· 434 434 * This is the main routine where commands issued by other 435 435 * cpus are handled. 436 436 */ 437 - static void do_ext_call_interrupt(unsigned int ext_int_code, 437 + static void do_ext_call_interrupt(struct ext_code ext_code, 438 438 unsigned int param32, unsigned long param64) 439 439 { 440 440 unsigned long bits; 441 441 int cpu; 442 442 443 443 cpu = smp_processor_id(); 444 - if ((ext_int_code & 0xffff) == 0x1202) 444 + if (ext_code.code == 0x1202) 445 445 kstat_cpu(cpu).irqs[EXTINT_EXC]++; 446 446 else 447 447 kstat_cpu(cpu).irqs[EXTINT_EMS]++;
+2 -2
arch/s390/kernel/time.c
··· 165 165 __ctl_set_bit(0, 4); 166 166 } 167 167 168 - static void clock_comparator_interrupt(unsigned int ext_int_code, 168 + static void clock_comparator_interrupt(struct ext_code ext_code, 169 169 unsigned int param32, 170 170 unsigned long param64) 171 171 { ··· 177 177 static void etr_timing_alert(struct etr_irq_parm *); 178 178 static void stp_timing_alert(struct stp_irq_parm *); 179 179 180 - static void timing_alert_interrupt(unsigned int ext_int_code, 180 + static void timing_alert_interrupt(struct ext_code ext_code, 181 181 unsigned int param32, unsigned long param64) 182 182 { 183 183 kstat_cpu(smp_processor_id()).irqs[EXTINT_TLA]++;
+1 -1
arch/s390/kernel/vtime.c
··· 220 220 /* 221 221 * Handler for the virtual CPU timer. 222 222 */ 223 - static void do_cpu_timer_interrupt(unsigned int ext_int_code, 223 + static void do_cpu_timer_interrupt(struct ext_code ext_code, 224 224 unsigned int param32, unsigned long param64) 225 225 { 226 226 struct vtimer_queue *vq;
+2 -2
arch/s390/mm/fault.c
··· 532 532 static DEFINE_SPINLOCK(pfault_lock); 533 533 static LIST_HEAD(pfault_list); 534 534 535 - static void pfault_interrupt(unsigned int ext_int_code, 535 + static void pfault_interrupt(struct ext_code ext_code, 536 536 unsigned int param32, unsigned long param64) 537 537 { 538 538 struct task_struct *tsk; ··· 545 545 * in the 'cpu address' field associated with the 546 546 * external interrupt. 547 547 */ 548 - subcode = ext_int_code >> 16; 548 + subcode = ext_code.subcode; 549 549 if ((subcode & 0xff00) != __SUBCODE_MASK) 550 550 return; 551 551 kstat_cpu(smp_processor_id()).irqs[EXTINT_PFL]++;
+3 -3
arch/s390/oprofile/hwsampler.c
··· 233 233 } 234 234 235 235 /* prototypes for external interrupt handler and worker */ 236 - static void hws_ext_handler(unsigned int ext_int_code, 237 - unsigned int param32, unsigned long param64); 236 + static void hws_ext_handler(struct ext_code ext_code, 237 + unsigned int param32, unsigned long param64); 238 238 239 239 static void worker(struct work_struct *work); 240 240 ··· 673 673 return rc; 674 674 } 675 675 676 - static void hws_ext_handler(unsigned int ext_int_code, 676 + static void hws_ext_handler(struct ext_code ext_code, 677 677 unsigned int param32, unsigned long param64) 678 678 { 679 679 struct hws_cpu_buffer *cb;
+4 -4
drivers/s390/block/dasd_diag.c
··· 229 229 } 230 230 231 231 /* Handle external interruption. */ 232 - static void dasd_ext_handler(unsigned int ext_int_code, 232 + static void dasd_ext_handler(struct ext_code ext_code, 233 233 unsigned int param32, unsigned long param64) 234 234 { 235 235 struct dasd_ccw_req *cqr, *next; ··· 239 239 addr_t ip; 240 240 int rc; 241 241 242 - switch (ext_int_code >> 24) { 242 + switch (ext_code.subcode >> 8) { 243 243 case DASD_DIAG_CODE_31BIT: 244 244 ip = (addr_t) param32; 245 245 break; ··· 280 280 cqr->stopclk = get_clock(); 281 281 282 282 expires = 0; 283 - if ((ext_int_code & 0xff0000) == 0) { 283 + if ((ext_code.subcode & 0xff) == 0) { 284 284 cqr->status = DASD_CQR_SUCCESS; 285 285 /* Start first request on queue if possible -> fast_io. */ 286 286 if (!list_empty(&device->ccw_queue)) { ··· 296 296 cqr->status = DASD_CQR_QUEUED; 297 297 DBF_DEV_EVENT(DBF_DEBUG, device, "interrupt status for " 298 298 "request %p was %d (%d retries left)", cqr, 299 - (ext_int_code >> 16) & 0xff, cqr->retries); 299 + ext_code.subcode & 0xff, cqr->retries); 300 300 dasd_diag_erp(device); 301 301 } 302 302
+2 -2
drivers/s390/char/sclp.c
··· 393 393 /* Handler for external interruption. Perform request post-processing. 394 394 * Prepare read event data request if necessary. Start processing of next 395 395 * request on queue. */ 396 - static void sclp_interrupt_handler(unsigned int ext_int_code, 396 + static void sclp_interrupt_handler(struct ext_code ext_code, 397 397 unsigned int param32, unsigned long param64) 398 398 { 399 399 struct sclp_req *req; ··· 818 818 819 819 /* Handler for external interruption used during initialization. Modify 820 820 * request state to done. */ 821 - static void sclp_check_handler(unsigned int ext_int_code, 821 + static void sclp_check_handler(struct ext_code ext_code, 822 822 unsigned int param32, unsigned long param64) 823 823 { 824 824 u32 finished_sccb;
+2 -4
drivers/s390/kvm/kvm_virtio.c
··· 380 380 /* 381 381 * we emulate the request_irq behaviour on top of s390 extints 382 382 */ 383 - static void kvm_extint_handler(unsigned int ext_int_code, 383 + static void kvm_extint_handler(struct ext_code ext_code, 384 384 unsigned int param32, unsigned long param64) 385 385 { 386 386 struct virtqueue *vq; 387 - u16 subcode; 388 387 u32 param; 389 388 390 - subcode = ext_int_code >> 16; 391 - if ((subcode & 0xff00) != VIRTIO_SUBCODE_64) 389 + if ((ext_code.subcode & 0xff00) != VIRTIO_SUBCODE_64) 392 390 return; 393 391 kstat_cpu(smp_processor_id()).irqs[EXTINT_VRT]++; 394 392
+1 -1
net/iucv/iucv.c
··· 1800 1800 * Handles external interrupts coming in from CP. 1801 1801 * Places the interrupt buffer on a queue and schedules iucv_tasklet_fn(). 1802 1802 */ 1803 - static void iucv_external_interrupt(unsigned int ext_int_code, 1803 + static void iucv_external_interrupt(struct ext_code ext_code, 1804 1804 unsigned int param32, unsigned long param64) 1805 1805 { 1806 1806 struct iucv_irq_data *p;