import of upstream 2.4.34.4 from kernel.org
[linux-2.4.git] / drivers / s390 / qdio.c
1 /*
2  *
3  * linux/drivers/s390/qdio.c
4  *
5  * Linux for S/390 QDIO base support, Hipersocket base support
6  * version 2
7  *
8  * Copyright 2000,2002 IBM Corporation
9  * Author(s): Utz Bacher <utz.bacher@de.ibm.com>
10  *
11  * Restriction: only 63 iqdio subchannels would have its own indicator,
12  * after that, subsequent subchannels share one indicator
13  *
14  *
15  *
16  *
17  * This program is free software; you can redistribute it and/or modify
18  * it under the terms of the GNU General Public License as published by
19  * the Free Software Foundation; either version 2, or (at your option)
20  * any later version.
21  *
22  * This program is distributed in the hope that it will be useful,
23  * but WITHOUT ANY WARRANTY; without even the implied warranty of
24  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
25  * GNU General Public License for more details.
26  *
27  * You should have received a copy of the GNU General Public License
28  * along with this program; if not, write to the Free Software
29  * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
30  */
31
32 /* we want the eyecatcher to be at the top of the code */
33 void volatile qdio_eyecatcher(void)
34 {
35         return;
36 }
37
38 #include <linux/config.h>
39
40 #include <linux/module.h>
41
42 #include <linux/version.h>
43 #include <linux/slab.h>
44 #include <linux/kernel.h>
45 #include <linux/proc_fs.h>
46 #include <linux/init.h>
47 #include <linux/timer.h>
48 #include <linux/mm.h>
49
50 #include <asm/irq.h>
51 #include <asm/io.h>
52 #include <asm/atomic.h>
53 #include <asm/semaphore.h>
54 #include <asm/page.h>
55
56 #include <asm/debug.h>
57
58 #include <asm/qdio.h>
59
60 #define VERSION_QDIO_C "$Revision: 1.145.4.9 $"
61
62 /****************** MODULE PARAMETER VARIABLES ********************/
63 MODULE_AUTHOR("Utz Bacher <utz.bacher@de.ibm.com>");
64 MODULE_DESCRIPTION("QDIO base support version 2, " \
65                    "Copyright 2000 IBM Corporation");
66 #if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,12))
67 MODULE_LICENSE("GPL");
68 #endif
69
70 /******************** HERE WE GO ***********************************/
71
72 static const char *version="QDIO base support version 2 ("
73         VERSION_QDIO_C "/" VERSION_QDIO_H ")";
74
75 #ifdef QDIO_PERFORMANCE_STATS
76 static int proc_perf_file_registration;
77 unsigned long i_p_c=0,i_p_nc=0,o_p_c=0,o_p_nc=0,ii_p_c=0,ii_p_nc=0;
78
79 static struct {
80         unsigned int tl_runs;
81
82         unsigned int siga_outs;
83         unsigned int siga_ins;
84         unsigned int siga_syncs;
85         unsigned int pcis;
86         unsigned int thinints;
87         unsigned int fast_reqs;
88
89         __u64 start_time_outbound;
90         unsigned int outbound_cnt;
91         unsigned int outbound_time;
92         __u64 start_time_inbound;
93         unsigned int inbound_cnt;
94         unsigned int inbound_time;
95 } perf_stats;
96
97 #endif /* QDIO_PERFORMANCE_STATS */
98
99 static int hydra_thinints=0;
100 static int omit_svs=0;
101
102 static int indicator_used[INDICATORS_PER_CACHELINE];
103 static __u32 * volatile indicators;
104 static __u32 volatile spare_indicator;
105 static atomic_t spare_indicator_usecount;
106
107 static debug_info_t *qdio_dbf_setup=NULL;
108 static debug_info_t *qdio_dbf_sbal=NULL;
109 static debug_info_t *qdio_dbf_trace=NULL;
110 static debug_info_t *qdio_dbf_sense=NULL;
111 #ifdef QDIO_DBF_LIKE_HELL
112 static debug_info_t *qdio_dbf_slsb_out=NULL;
113 static debug_info_t *qdio_dbf_slsb_in=NULL;
114 #endif /* QDIO_DBF_LIKE_HELL */
115
116 static qdio_irq_t *first_irq[QDIO_IRQ_BUCKETS]={
117         [0 ... (QDIO_IRQ_BUCKETS-1)] = NULL
118 };
119 static rwlock_t irq_list_lock[QDIO_IRQ_BUCKETS]={
120         [0 ... (QDIO_IRQ_BUCKETS-1)] = RW_LOCK_UNLOCKED
121 };
122
123 static struct semaphore init_sema;
124
125 static qdio_chsc_area_t *chsc_area;
126 static spinlock_t chsc_area_lock=SPIN_LOCK_UNLOCKED;
127 /* iQDIO stuff: */
128 static volatile qdio_q_t *tiq_list=NULL; /* volatile as it could change
129                                            during a while loop */
130 static spinlock_t ttiq_list_lock=SPIN_LOCK_UNLOCKED;
131 static int register_thinint_result;
132 static void tiqdio_tl(unsigned long);
133 static DECLARE_TASKLET(tiqdio_tasklet,tiqdio_tl,0);
134
135 #define HEXDUMP16(importance,header,ptr) \
136 QDIO_PRINT_##importance(header "%02x %02x %02x %02x  " \
137                         "%02x %02x %02x %02x  %02x %02x %02x %02x  " \
138                         "%02x %02x %02x %02x\n",*(((char*)ptr)), \
139                         *(((char*)ptr)+1),*(((char*)ptr)+2), \
140                         *(((char*)ptr)+3),*(((char*)ptr)+4), \
141                         *(((char*)ptr)+5),*(((char*)ptr)+6), \
142                         *(((char*)ptr)+7),*(((char*)ptr)+8), \
143                         *(((char*)ptr)+9),*(((char*)ptr)+10), \
144                         *(((char*)ptr)+11),*(((char*)ptr)+12), \
145                         *(((char*)ptr)+13),*(((char*)ptr)+14), \
146                         *(((char*)ptr)+15)); \
147 QDIO_PRINT_##importance(header "%02x %02x %02x %02x  %02x %02x %02x %02x  " \
148                         "%02x %02x %02x %02x  %02x %02x %02x %02x\n", \
149                         *(((char*)ptr)+16),*(((char*)ptr)+17), \
150                         *(((char*)ptr)+18),*(((char*)ptr)+19), \
151                         *(((char*)ptr)+20),*(((char*)ptr)+21), \
152                         *(((char*)ptr)+22),*(((char*)ptr)+23), \
153                         *(((char*)ptr)+24),*(((char*)ptr)+25), \
154                         *(((char*)ptr)+26),*(((char*)ptr)+27), \
155                         *(((char*)ptr)+28),*(((char*)ptr)+29), \
156                         *(((char*)ptr)+30),*(((char*)ptr)+31));
157
158 #define atomic_swap(a,b) xchg((int*)a.counter,b)
159
160 /* not a macro, as one of the arguments is atomic_read */
161 static inline int qdio_min(int a,int b)
162 {
163         if (a<b)
164                 return a;
165         else
166                 return b;
167 }
168
169 /* unlikely as the later the better */
170 #define SYNC_MEMORY if (unlikely(q->siga_sync)) qdio_siga_sync_q(q)
171 #define SYNC_MEMORY_ALL if (unlikely(q->siga_sync)) \
172         qdio_siga_sync(q,~0U,~0U)
173 #define SYNC_MEMORY_ALL_OUTB if (unlikely(q->siga_sync)) \
174         qdio_siga_sync(q,~0U,0)
175
176 #define NOW qdio_get_micros()
177 #define SAVE_TIMESTAMP(q) q->timing.last_transfer_time=NOW
178 #define GET_SAVED_TIMESTAMP(q) (q->timing.last_transfer_time)
179 #define SAVE_FRONTIER(q,val) q->last_move_ftc=val
180 #define GET_SAVED_FRONTIER(q) (q->last_move_ftc)
181
182 #define MY_MODULE_STRING(x) #x
183
184 #ifdef QDIO_32_BIT
185 #define QDIO_GET_32BIT_ADDR(x) ((__u32)(long)x)
186 #else /* QDIO_32_BIT */
187 #define QDIO_GET_32BIT_ADDR(x) ((__u32)(unsigned long)x)
188 #endif /* QDIO_32_BIT */
189
190 #define QDIO_PFIX_GET_ADDR(x) ((flags&QDIO_PFIX) ? \
191                                pfix_get_addr(x):((unsigned long)x))
192
193 /***************** SCRUBBER HELPER ROUTINES **********************/
194
195 static inline volatile __u64 qdio_get_micros(void)
196 {
197         __u64 time;
198
199         asm volatile ("STCK %0" : "=m" (time));
200         return time>>12; /* time>>12 is microseconds*/
201 }
202 static inline unsigned long qdio_get_millis(void)
203 {
204         return (unsigned long)(qdio_get_micros()>>10);
205 }
206
207 static __inline__ int atomic_return_add (int i, atomic_t *v)
208 {
209         int old, new;
210         __CS_LOOP(old, new, v, i, "ar");
211         return old;
212 }
213
214 static void qdio_wait_nonbusy(unsigned int timeout)
215 {
216         unsigned int start;
217         char dbf_text[15];
218
219         sprintf(dbf_text,"wtnb%4x",timeout);
220         QDIO_DBF_TEXT3(0,trace,dbf_text);
221
222         start=qdio_get_millis();
223         for (;;) {
224                 set_task_state(current,TASK_INTERRUPTIBLE);
225                 if (qdio_get_millis()-start>timeout) {
226                         goto out;
227                 }
228                 schedule_timeout(((start+timeout-qdio_get_millis())>>10)*HZ);
229         }
230 out:
231         set_task_state(current,TASK_RUNNING);
232 }
233
234 static int qdio_wait_for_no_use_count(atomic_t *use_count)
235 {
236         unsigned long start;
237
238         QDIO_DBF_TEXT3(0,trace,"wtnousec");
239         start=qdio_get_millis();
240         for (;;) {
241                 if (qdio_get_millis()-start>QDIO_NO_USE_COUNT_TIMEOUT) {
242                         QDIO_DBF_TEXT1(1,trace,"WTNOUSTO");
243                         return -ETIME;
244                 }
245                 if (!atomic_read(use_count)) {
246                         QDIO_DBF_TEXT3(0,trace,"wtnoused");
247                         return 0;
248                 }
249                 qdio_wait_nonbusy(QDIO_NO_USE_COUNT_TIME);
250         }
251 }
252
253 /* unfortunately, we can't just xchg the values; in do_QDIO we want to reserve
254  * the q in any case, so that we'll not be interrupted when we are in
255  * qdio_mark_tiq... shouldn't have a really bad impact, as reserving almost
256  * ever works (last famous words) */
257 static inline int qdio_reserve_q(qdio_q_t *q)
258 {
259         return atomic_return_add(1,&q->use_count);
260 }
261
262 static inline void qdio_release_q(qdio_q_t *q)
263 {
264         atomic_dec(&q->use_count);
265 }
266 #ifdef QDIO_DBF_LIKE_HELL 
267 #define set_slsb(x,y) \
268   if(q->queue_type==QDIO_TRACE_QTYPE) { \
269         if(q->is_input_q) { \
270             QDIO_DBF_HEX2(0,slsb_in,&q->slsb,QDIO_MAX_BUFFERS_PER_Q); \
271         } else { \
272             QDIO_DBF_HEX2(0,slsb_out,&q->slsb,QDIO_MAX_BUFFERS_PER_Q); \
273         } \
274   } \
275   qdio_set_slsb(x,y); \
276   if(q->queue_type==QDIO_TRACE_QTYPE) { \
277         if(q->is_input_q) { \
278             QDIO_DBF_HEX2(0,slsb_in,&q->slsb,QDIO_MAX_BUFFERS_PER_Q); \
279         } else { \
280             QDIO_DBF_HEX2(0,slsb_out,&q->slsb,QDIO_MAX_BUFFERS_PER_Q); \
281         } \
282   }
283 #else /* QDIO_DBF_LIKE_HELL */
284 #define set_slsb(x,y) qdio_set_slsb(x,y)
285 #endif /* QDIO_DBF_LIKE_HELL */
286 static volatile inline void qdio_set_slsb(volatile char *slsb,
287                                           unsigned char value)
288 {
289         xchg((char*)slsb,value);
290 }
291
292 static inline int qdio_siga_sync(qdio_q_t *q,
293                                  unsigned int gpr2,
294                                  unsigned int gpr3)
295 {
296         int cc;
297
298 #ifdef QDIO_DBF_LIKE_HELL
299         QDIO_DBF_TEXT4(0,trace,"sigasync");
300         QDIO_DBF_HEX4(0,trace,&q,sizeof(int));
301         QDIO_DBF_HEX4(0,trace,&gpr2,sizeof(int));
302         QDIO_DBF_HEX4(0,trace,&gpr3,sizeof(int));
303 #endif /* QDIO_DBF_LIKE_HELL */
304
305 #ifdef QDIO_PERFORMANCE_STATS
306         perf_stats.siga_syncs++;
307 #endif /* QDIO_PERFORMANCE_STATS */
308
309 #ifdef QDIO_32_BIT
310         asm volatile (
311                 "lhi    0,2     \n\t"
312                 "lr     1,%1    \n\t"
313                 "lr     2,%2    \n\t"
314                 "lr     3,%3    \n\t"
315                 "siga   0       \n\t"
316                 "ipm    %0      \n\t"
317                 "srl    %0,28   \n\t"
318                 : "=d" (cc)
319                 : "d" (0x10000|q->irq), "d" (gpr2), "d" (gpr3)
320                 : "cc", "0", "1", "2", "3"
321                 );
322 #else /* QDIO_32_BIT */
323         asm volatile (
324                 "lghi   0,2     \n\t"
325                 "llgfr  1,%1    \n\t"
326                 "llgfr  2,%2    \n\t"
327                 "llgfr  3,%3    \n\t"
328                 "siga   0       \n\t"
329                 "ipm    %0      \n\t"
330                 "srl    %0,28   \n\t"
331                 : "=d" (cc)
332                 : "d" (0x10000|q->irq), "d" (gpr2), "d" (gpr3)
333                 : "cc", "0", "1", "2", "3"
334                 );
335 #endif /* QDIO_32_BIT */
336
337         if (cc) {
338 #ifndef QDIO_DBF_LIKE_HELL
339                 /* when QDIO_DBF_LIKE_HELL, we put that already out */
340                 QDIO_DBF_TEXT3(0,trace,"sigasync");
341                 QDIO_DBF_HEX3(0,trace,&q,sizeof(void*));
342 #endif /* QDIO_DBF_LIKE_HELL */
343                 QDIO_DBF_HEX3(0,trace,&cc,sizeof(int*));
344         }
345
346         return cc;
347 }
348
349 static inline int qdio_siga_sync_q(qdio_q_t *q)
350 {
351         if (q->is_input_q) {
352                 return qdio_siga_sync(q,0,q->mask);
353         } else {
354                 return qdio_siga_sync(q,q->mask,0);
355         }
356 }
357
358 /* returns QDIO_SIGA_ERROR_ACCESS_EXCEPTION as cc, when SIGA returns
359    an access exception */
360 static inline int qdio_siga_output(qdio_q_t *q)
361 {
362         int cc;
363         __u32 busy_bit;
364         __u64 start_time=0;
365
366 #ifdef QDIO_PERFORMANCE_STATS
367         perf_stats.siga_outs++;
368 #endif /* QDIO_PERFORMANCE_STATS */
369
370 #ifdef QDIO_DBF_LIKE_HELL
371         QDIO_DBF_TEXT4(0,trace,"sigaout");
372         QDIO_DBF_HEX4(0,trace,&q,sizeof(void*));
373 #endif /* QDIO_DBF_LIKE_HELL */
374
375         for (;;) {
376
377 #ifdef QDIO_32_BIT
378                 asm volatile (
379                       "lhi      0,0     \n\t"
380                       "lr       1,%2    \n\t"
381                       "lr       2,%3    \n\t"
382                       "siga     0       \n\t"
383                       "0:"
384                       "ipm      %0      \n\t"
385                       "srl      %0,28   \n\t"
386                       "srl      0,31    \n\t"
387                       "lr       %1,0    \n\t"
388                       "1:       \n\t"
389                       ".section .fixup,\"ax\"\n\t"
390                       "2:       \n\t"
391                       "lhi      %0,%4   \n\t"
392                       "bras     1,3f    \n\t"
393                       ".long 1b \n\t"
394                       "3:       \n\t"
395                       "l        1,0(1)  \n\t"
396                       "br       1       \n\t"
397                       ".previous        \n\t"
398                       ".section __ex_table,\"a\"\n\t"
399                       ".align 4 \n\t"
400                       ".long    0b,2b   \n\t"
401                       ".previous        \n\t"
402                         : "=d" (cc), "=d" (busy_bit)
403                         : "d" (0x10000|q->irq), "d" (q->mask),
404                         "i" (QDIO_SIGA_ERROR_ACCESS_EXCEPTION)
405                         : "cc", "0", "1", "2", "memory"
406                 );
407 #else /* QDIO_32_BIT */
408                 asm volatile (
409                       "lghi     0,0     \n\t"
410                       "llgfr    1,%2    \n\t"
411                       "llgfr    2,%3    \n\t"
412                       "siga     0       \n\t"
413                       "0:"
414                       "ipm      %0      \n\t"
415                       "srl      %0,28   \n\t"
416                       "srl      0,31    \n\t"
417                       "llgfr    %1,0    \n\t"
418                       "1:       \n\t"
419                       ".section .fixup,\"ax\"\n\t"
420                       "lghi     %0,%4   \n\t"
421                       "jg       1b      \n\t"
422                       ".previous\n\t"
423                       ".section __ex_table,\"a\"\n\t"
424                       ".align 8 \n\t"
425                       ".quad    0b,1b   \n\t"
426                       ".previous        \n\t"
427                       : "=d" (cc), "=d" (busy_bit)
428                       : "d" (0x10000|q->irq), "d" (q->mask),
429                       "i" (QDIO_SIGA_ERROR_ACCESS_EXCEPTION)
430                       : "cc", "0", "1", "2", "memory"
431              );
432 #endif /* QDIO_32_BIT */
433
434 //QDIO_PRINT_ERR("cc=%x, busy=%x\n",cc,busy_bit);
435              if ( (cc==2) && (busy_bit) &&
436                   (q->is_iqdio_q) ) {
437                      if (!start_time) start_time=NOW;
438                      if ((NOW-start_time)>QDIO_BUSY_BIT_PATIENCE)
439                              break;
440              } else
441                      break;
442         }
443
444         if ((cc==2) && (busy_bit)) cc|=QDIO_SIGA_ERROR_B_BIT_SET;
445
446         if (cc) {
447 #ifndef QDIO_DBF_LIKE_HELL
448                 QDIO_DBF_TEXT3(0,trace,"sigaout");
449                 QDIO_DBF_HEX3(0,trace,&q,sizeof(void*));
450 #endif /* QDIO_DBF_LIKE_HELL */
451                 QDIO_DBF_HEX3(0,trace,&cc,sizeof(int*));
452         }
453
454         return cc;
455 }
456
457 static inline int qdio_siga_input(qdio_q_t *q)
458 {
459         int cc;
460
461 #ifdef QDIO_DBF_LIKE_HELL
462         QDIO_DBF_TEXT4(0,trace,"sigain");
463         QDIO_DBF_HEX4(0,trace,&q,sizeof(void*));
464 #endif /* QDIO_DBF_LIKE_HELL */
465
466 #ifdef QDIO_PERFORMANCE_STATS
467         perf_stats.siga_ins++;
468 #endif /* QDIO_PERFORMANCE_STATS */
469
470 #ifdef QDIO_32_BIT
471         asm volatile (
472                 "lhi    0,1     \n\t"
473                 "lr     1,%1    \n\t"
474                 "lr     2,%2    \n\t"
475                 "siga   0       \n\t"
476                 "ipm    %0      \n\t"
477                 "srl    %0,28   \n\t"
478                 : "=d" (cc)
479                 : "d" (0x10000|q->irq), "d" (q->mask)
480                 : "cc", "0", "1", "2", "memory"
481                 );
482 #else /* QDIO_32_BIT */
483         asm volatile (
484                 "lghi   0,1     \n\t"
485                 "llgfr  1,%1    \n\t"
486                 "llgfr  2,%2    \n\t"
487                 "siga   0       \n\t"
488                 "ipm    %0      \n\t"
489                 "srl    %0,28   \n\t"
490                 : "=d" (cc)
491                 : "d" (0x10000|q->irq), "d" (q->mask)
492                 : "cc", "0", "1", "2", "memory"
493                 );
494 #endif /* QDIO_32_BIT */
495
496         if (cc) {
497 #ifndef QDIO_DBF_LIKE_HELL
498                 QDIO_DBF_TEXT3(0,trace,"sigain");
499                 QDIO_DBF_HEX3(0,trace,&q,sizeof(void*));
500 #endif /* QDIO_DBF_LIKE_HELL */
501                 QDIO_DBF_HEX3(0,trace,&cc,sizeof(int*));
502         }
503
504         return cc;
505 }
506
507 /* locked by the locks in qdio_activate and qdio_cleanup */
508 static __u32 * volatile qdio_get_indicator(void)
509 {
510         int i=1;
511         int found=0;
512
513         while (i<INDICATORS_PER_CACHELINE) {
514                 if (!indicator_used[i]) {
515                         indicator_used[i]=1;
516                         found=1;
517                         break;
518                 }
519                 i++;
520         }
521
522         if (found)
523                 return indicators+i;
524         else {
525                 atomic_inc(&spare_indicator_usecount);
526                 return (__u32 * volatile) &spare_indicator;
527         }
528 }
529
530 /* locked by the locks in qdio_activate and qdio_cleanup */
531 static void qdio_put_indicator(__u32 *addr)
532 {
533         int i;
534
535         if ( (addr) && (addr!=&spare_indicator) ) {
536                 i=addr-indicators;
537                 indicator_used[i]=0;
538         }
539         if (addr==&spare_indicator) {
540                 atomic_dec(&spare_indicator_usecount);
541         }
542 }
543
544 static inline volatile void tiqdio_clear_summary_bit(__u32 *location)
545 {
546 #ifdef QDIO_DBF_LIKE_HELL
547         QDIO_DBF_TEXT5(0,trace,"clrsummb");
548         QDIO_DBF_HEX5(0,trace,&location,sizeof(void*));
549 #endif /* QDIO_DBF_LIKE_HELL */
550         xchg(location,0);
551 }
552
553 static inline volatile void tiqdio_set_summary_bit(__u32 *location)
554 {
555 #ifdef QDIO_DBF_LIKE_HELL
556         QDIO_DBF_TEXT5(0,trace,"setsummb");
557         QDIO_DBF_HEX5(0,trace,&location,sizeof(void*));
558 #endif /* QDIO_DBF_LIKE_HELL */
559         xchg(location,-1);
560 }
561
562 static inline void tiqdio_sched_tl(void)
563 {
564         tasklet_hi_schedule(&tiqdio_tasklet);
565 }
566
567 static inline void qdio_mark_tiq(qdio_q_t *q)
568 {
569         unsigned long flags;
570 #ifdef QDIO_DBF_LIKE_HELL
571         QDIO_DBF_TEXT4(0,trace,"mark iq");
572         QDIO_DBF_HEX4(0,trace,&q,sizeof(void*));
573 #endif /* QDIO_DBF_LIKE_HELL */
574
575         spin_lock_irqsave(&ttiq_list_lock,flags);
576         if (unlikely(atomic_read(&q->is_in_shutdown))) goto out_unlock;
577
578         if (q->is_input_q) {
579                 if ((q->list_prev) || (q->list_next)) goto out_unlock;
580
581                 if (!tiq_list) {
582                         tiq_list=q;
583                         q->list_prev=q;
584                         q->list_next=q;
585                 } else {
586                         q->list_next=tiq_list;
587                         q->list_prev=tiq_list->list_prev;
588                         tiq_list->list_prev->list_next=q;
589                         tiq_list->list_prev=q;
590                 }
591                 spin_unlock_irqrestore(&ttiq_list_lock,flags);
592
593                 tiqdio_set_summary_bit((__u32*)q->dev_st_chg_ind);
594                 tiqdio_sched_tl();
595         }
596         return;
597 out_unlock:
598         spin_unlock_irqrestore(&ttiq_list_lock,flags);
599         return;
600 }
601
602 static inline void qdio_mark_q(qdio_q_t *q)
603 {
604 #ifdef QDIO_DBF_LIKE_HELL
605         QDIO_DBF_TEXT4(0,trace,"mark q");
606         QDIO_DBF_HEX4(0,trace,&q,sizeof(void*));
607 #endif /* QDIO_DBF_LIKE_HELL */
608
609         if (unlikely(atomic_read(&q->is_in_shutdown))) return;
610
611         tasklet_schedule(&q->tasklet);
612 }
613
614 static inline int qdio_stop_polling(qdio_q_t *q)
615 {
616 #ifdef QDIO_USE_PROCESSING_STATE
617         int gsf;
618
619         if (!atomic_swap(&q->polling,0)) return 1;
620
621 #ifdef QDIO_DBF_LIKE_HELL
622         QDIO_DBF_TEXT4(0,trace,"stoppoll");
623         QDIO_DBF_HEX4(0,trace,&q,sizeof(void*));
624 #endif /* QDIO_DBF_LIKE_HELL */
625
626         /* show the card that we are not polling anymore */
627         if (q->is_input_q) {
628                 gsf=GET_SAVED_FRONTIER(q);
629                 set_slsb(&q->slsb.acc.val[(gsf+QDIO_MAX_BUFFERS_PER_Q-1)&
630                          (QDIO_MAX_BUFFERS_PER_Q-1)],SLSB_P_INPUT_NOT_INIT);
631                 /* we don't issue this SYNC_MEMORY, as we trust Rick T and
632                  * moreover will not use the PROCESSING state under VM,
633                  * so q->polling was 0 anyway.
634                 SYNC_MEMORY;*/
635                 if (q->slsb.acc.val[gsf]==SLSB_P_INPUT_PRIMED) {
636                         /* set our summary bit again, as otherwise there is a
637                          * small window we can miss between resetting it and
638                          * checking for PRIMED state */
639                         if (q->is_thinint_q)
640                                 tiqdio_set_summary_bit
641                                         ((__u32*)q->dev_st_chg_ind);
642                         return 0;
643                 }
644         }
645 #endif /* QDIO_USE_PROCESSING_STATE */
646         return 1;
647 }
648
649 /* see the comment in do_QDIO and before qdio_reserve_q about the
650  * sophisticated locking outside of unmark_q, so that we don't need to
651  * disable the interrupts :-) */
652 static inline void qdio_unmark_q(qdio_q_t *q)
653 {
654         unsigned long flags;
655
656 #ifdef QDIO_DBF_LIKE_HELL
657         QDIO_DBF_TEXT4(0,trace,"unmark q");
658         QDIO_DBF_HEX4(0,trace,&q,sizeof(void*));
659 #endif /* QDIO_DBF_LIKE_HELL */
660
661         if ((!q->list_prev)||(!q->list_next)) return;
662
663         if ((q->is_thinint_q)&&(q->is_input_q)) {
664                 /* iQDIO */
665                 spin_lock_irqsave(&ttiq_list_lock,flags);
666                 /* in case cleanup has done this already and simultanously
667                  * qdio_unmark_q is called from the interrupt handler, we've
668                  * got to check this in this specific case again */
669                 if ((!q->list_prev)||(!q->list_next))
670                         goto out;
671                 if (q->list_next==q) {
672                         /* q was the only interesting q */
673                         tiq_list=NULL;
674                         q->list_next=NULL;
675                         q->list_prev=NULL;
676                 } else {
677                         q->list_next->list_prev=q->list_prev;
678                         q->list_prev->list_next=q->list_next;
679                         tiq_list=q->list_next;
680                         q->list_next=NULL;
681                         q->list_prev=NULL;
682                 }
683 out:
684                 spin_unlock_irqrestore(&ttiq_list_lock,flags);
685         }
686 }
687
688 static inline volatile unsigned long tiqdio_clear_global_summary(void)
689 {
690         unsigned long time;
691
692 #ifdef QDIO_DBF_LIKE_HELL
693         QDIO_DBF_TEXT5(0,trace,"clrglobl");
694 #endif /* QDIO_DBF_LIKE_HELL */
695
696 #ifdef QDIO_32_BIT
697         asm volatile (
698                 "lhi    1,3     \n\t"
699                 ".insn  rre,0xb2650000,2,0      \n\t"
700                 "lr     %0,3    \n\t"
701                 : "=d" (time) : : "cc", "1", "2", "3"
702                 );
703 #else /* QDIO_32_BIT */
704         asm volatile (
705                 "lghi   1,3     \n\t"
706                 ".insn  rre,0xb2650000,2,0      \n\t"
707                 "lgr    %0,3    \n\t"
708                 : "=d" (time) : : "cc", "1", "2", "3"
709                 );
710 #endif /* QDIO_32_BIT */
711
712 #ifdef QDIO_DBF_LIKE_HELL
713         QDIO_DBF_HEX5(0,trace,&time,sizeof(unsigned long));
714 #endif /* QDIO_DBF_LIKE_HELL */
715         return time;
716 }
717
718 /************************* OUTBOUND ROUTINES *******************************/
719
720 static inline void qdio_translate_buffer_back(qdio_q_t *q,int bufno)
721 {
722         if (unlikely(!q->is_0copy_sbals_q))
723                 memcpy(q->qdio_buffers[bufno],
724                        (void*)q->sbal[bufno],SBAL_SIZE);
725 }
726
727 static inline int qdio_get_outbound_buffer_frontier(qdio_q_t *q)
728 {
729         int f,f_mod_no;
730         volatile char *slsb;
731         int first_not_to_check;
732         char dbf_text[15];
733         char slsbyte;
734
735 #ifdef QDIO_DBF_LIKE_HELL
736         QDIO_DBF_TEXT4(0,trace,"getobfro");
737         QDIO_DBF_HEX4(0,trace,&q,sizeof(void*));
738 #endif /* QDIO_DBF_LIKE_HELL */
739
740         slsb=&q->slsb.acc.val[0];
741         f_mod_no=f=q->first_to_check;
742         /* f point to already processed elements, so f+no_used is correct...
743          * ... but: we don't check 128 buffers, as otherwise
744          * qdio_has_outbound_q_moved would return 0 */
745         first_not_to_check=f+qdio_min(atomic_read(&q->number_of_buffers_used),
746                                       (QDIO_MAX_BUFFERS_PER_Q-1));
747
748         if ((!q->is_iqdio_q)&&(!q->hydra_gives_outbound_pcis)) {
749                 SYNC_MEMORY;
750         }
751
752 check_next:
753         if (f==first_not_to_check) goto out;
754         slsbyte=slsb[f_mod_no];
755
756         /* the card has not fetched the output yet */
757         if (slsbyte==SLSB_CU_OUTPUT_PRIMED) {
758 #ifdef QDIO_DBF_LIKE_HELL
759                 QDIO_DBF_TEXT5(0,trace,"outpprim");
760 #endif /* QDIO_DBF_LIKE_HELL */
761                 goto out;
762         }
763
764         /* the card got it */
765         if (slsbyte==SLSB_P_OUTPUT_EMPTY) {
766                 atomic_dec(&q->number_of_buffers_used);
767                 f++;
768                 f_mod_no=f&(QDIO_MAX_BUFFERS_PER_Q-1);
769 #ifdef QDIO_DBF_LIKE_HELL
770                 QDIO_DBF_TEXT5(0,trace,"outpempt");
771 #endif /* QDIO_DBF_LIKE_HELL */
772                 goto check_next;
773         }
774
775         if (slsbyte==SLSB_P_OUTPUT_ERROR) {
776                 QDIO_DBF_TEXT3(0,trace,"outperr");
777                 sprintf(dbf_text,"%x-%x-%x",f_mod_no,
778                         q->sbal[f_mod_no]->element[14].sbalf.value,
779                         q->sbal[f_mod_no]->element[15].sbalf.value);
780                 QDIO_DBF_TEXT3(1,trace,dbf_text);
781                 QDIO_DBF_HEX2(1,sbal,q->sbal[f_mod_no],256);
782
783                 /* kind of process the buffer */
784                 set_slsb(&q->slsb.acc.val[f_mod_no],
785                          SLSB_P_OUTPUT_NOT_INIT);
786
787                 qdio_translate_buffer_back(q,f_mod_no);
788
789                 /* we increment the frontier, as this buffer
790                  * was processed obviously */
791                 atomic_dec(&q->number_of_buffers_used);
792                 f_mod_no=(f_mod_no+1)&(QDIO_MAX_BUFFERS_PER_Q-1);
793
794                 if (q->qdio_error)
795                         q->error_status_flags|=
796                                 QDIO_STATUS_MORE_THAN_ONE_QDIO_ERROR;
797                 q->qdio_error=SLSB_P_OUTPUT_ERROR;
798                 q->error_status_flags|=QDIO_STATUS_LOOK_FOR_ERROR;
799
800                 goto out;
801         }
802
803         /* no new buffers */
804 #ifdef QDIO_DBF_LIKE_HELL
805         QDIO_DBF_TEXT5(0,trace,"outpni");
806 #endif /* QDIO_DBF_LIKE_HELL */
807         goto out;
808
809 out:
810         return (q->first_to_check=f_mod_no);
811 }
812
813 /* all buffers are processed */
814 static inline int qdio_is_outbound_q_done(qdio_q_t *q)
815 {
816         int no_used;
817 #ifdef QDIO_DBF_LIKE_HELL
818         char dbf_text[15];
819 #endif /* QDIO_DBF_LIKE_HELL */
820
821         no_used=atomic_read(&q->number_of_buffers_used);
822
823 #ifdef QDIO_DBF_LIKE_HELL
824         if (no_used) {
825                 sprintf(dbf_text,"oqisnt%02x",no_used);
826                 QDIO_DBF_TEXT4(0,trace,dbf_text);
827         } else {
828                 QDIO_DBF_TEXT4(0,trace,"oqisdone");
829         }
830         QDIO_DBF_HEX4(0,trace,&q,sizeof(void*));
831 #endif /* QDIO_DBF_LIKE_HELL */
832         return (no_used==0);
833 }
834
835 static inline int qdio_has_outbound_q_moved(qdio_q_t *q)
836 {
837         int i;
838
839         i=qdio_get_outbound_buffer_frontier(q);
840
841         if ( (i!=GET_SAVED_FRONTIER(q)) ||
842              (q->error_status_flags&QDIO_STATUS_LOOK_FOR_ERROR) ) {
843                 SAVE_FRONTIER(q,i);
844 #ifdef QDIO_DBF_LIKE_HELL
845                 QDIO_DBF_TEXT4(0,trace,"oqhasmvd");
846                 QDIO_DBF_HEX4(0,trace,&q,sizeof(void*));
847 #endif /* QDIO_DBF_LIKE_HELL */
848                 return 1;
849         } else {
850 #ifdef QDIO_DBF_LIKE_HELL
851                 QDIO_DBF_TEXT4(0,trace,"oqhsntmv");
852                 QDIO_DBF_HEX4(0,trace,&q,sizeof(void*));
853 #endif /* QDIO_DBF_LIKE_HELL */
854                 return 0;
855         }
856 }
857
858 static inline void qdio_kick_outbound_q(qdio_q_t *q)
859 {
860         int result;
861         char dbf_text[15];
862 #ifdef QDIO_DBF_LIKE_HELL
863         QDIO_DBF_TEXT4(0,trace,"kickoutq");
864         QDIO_DBF_HEX4(0,trace,&q,sizeof(void*));
865 #endif /* QDIO_DBF_LIKE_HELL */
866
867         if (!q->siga_out) return;
868
869         /* here's the story with cc=2 and busy bit set (thanks, Rick):
870          * VM's CP could present us cc=2 and busy bit set on SIGA-write
871          * during reconfiguration of their Guest LAN (only in HIPERS mode,
872          * QDIO mode is asynchronous -- cc=2 and busy bit there will take
873          * the queues down immediately; and not being under VM we have a
874          * problem on cc=2 and busy bit set right away).
875          *
876          * Therefore qdio_siga_output will try for a short time constantly,
877          * if such a condition occurs. If it doesn't change, it will
878          * increase the busy_siga_counter and save the timestamp, and
879          * schedule the queue for later processing (via mark_q, using the
880          * queue tasklet). __qdio_outbound_processing will check out the
881          * counter. If non-zero, it will call qdio_kick_outbound_q as often
882          * as the value of the counter. This will attempt further SIGA
883          * instructions.
884          * Every successful SIGA instruction will decrease the counter.
885          * After some time of no movement, qdio_kick_outbound_q will
886          * finally fail and reflect corresponding error codes to call
887          * the upper layer module and have it take the queues down.
888          *
889          * Note that this is a change from the original HiperSockets design
890          * (saying cc=2 and busy bit means take the queues down), but in
891          * these days Guest LAN didn't exist... excessive cc=2 with busy bit
892          * conditions will still take the queues down, but the threshold is
893          * higher due to the Guest LAN environment.
894          */
895
896         result=qdio_siga_output(q);
897
898                 switch (result) {
899                 case 0:
900                 /* went smooth this time, reset timestamp */
901                         QDIO_DBF_TEXT3(0,trace,"cc2reslv");
902                         sprintf(dbf_text,"%4x%2x%2x",q->irq,q->q_no,
903                                 atomic_read(&q->busy_siga_counter));
904                         QDIO_DBF_TEXT3(0,trace,dbf_text);
905                         q->timing.busy_start=0;
906                         break;
907                 case (2|QDIO_SIGA_ERROR_B_BIT_SET):
908                         /* cc=2 and busy bit: */
909                 atomic_inc(&q->busy_siga_counter);
910
911                         /* if the last siga was successful, save
912                          * timestamp here */
913                         if (!q->timing.busy_start)
914                                 q->timing.busy_start=NOW;
915
916                         /* if we're in time, don't touch error_status_flags
917                          * and siga_error */
918                         if (NOW-q->timing.busy_start<QDIO_BUSY_BIT_GIVE_UP) {
919                                 qdio_mark_q(q);
920                                 break;
921                         }
922                         QDIO_DBF_TEXT2(0,trace,"cc2REPRT");
923                         sprintf(dbf_text,"%4x%2x%2x",q->irq,q->q_no,
924                                 atomic_read(&q->busy_siga_counter));
925                         QDIO_DBF_TEXT3(0,trace,dbf_text);
926                         /* else fallthrough and report error */
927                 default:
928                         /* for plain cc=1, 2 or 3: */
929                 if (q->siga_error)
930                         q->error_status_flags|=
931                                 QDIO_STATUS_MORE_THAN_ONE_SIGA_ERROR;
932                 q->error_status_flags|=
933                         QDIO_STATUS_LOOK_FOR_ERROR;
934                 q->siga_error=result;
935         }
936 }
937
938 static inline void qdio_kick_outbound_handler(qdio_q_t *q)
939 {
940 #ifdef QDIO_DBF_LIKE_HELL
941         char dbf_text[15];
942 #endif /* QDIO_DBF_LIKE_HELL */
943
944         int start=q->first_element_to_kick;
945         /* last_move_ftc was just updated */
946         int real_end=GET_SAVED_FRONTIER(q);
947         int end=(real_end+QDIO_MAX_BUFFERS_PER_Q-1)&
948                 (QDIO_MAX_BUFFERS_PER_Q-1);
949         int count=(end+QDIO_MAX_BUFFERS_PER_Q+1-start)&
950                 (QDIO_MAX_BUFFERS_PER_Q-1);
951
952 #ifdef QDIO_DBF_LIKE_HELL
953         QDIO_DBF_TEXT4(0,trace,"kickouth");
954         QDIO_DBF_HEX4(0,trace,&q,sizeof(void*));
955 #endif /* QDIO_DBF_LIKE_HELL */
956
957 #ifdef QDIO_DBF_LIKE_HELL
958         sprintf(dbf_text,"s=%2xc=%2x",start,count);
959         QDIO_DBF_TEXT4(0,trace,dbf_text);
960 #endif /* QDIO_DBF_LIKE_HELL */
961
962         if (q->state==QDIO_IRQ_STATE_ACTIVE)
963                 q->handler(q->irq,QDIO_STATUS_OUTBOUND_INT|
964                            q->error_status_flags,
965                            q->qdio_error,q->siga_error,q->q_no,start,count,
966                            q->int_parm);
967
968         /* for the next time: */
969         q->first_element_to_kick=real_end;
970         q->qdio_error=0;
971         q->siga_error=0;
972         q->error_status_flags=0;
973 }
974
975 static inline void __qdio_outbound_processing(qdio_q_t *q)
976 {
977         int siga_attempts;
978 #ifdef QDIO_DBF_LIKE_HELL
979         QDIO_DBF_TEXT4(0,trace,"qoutproc");
980         QDIO_DBF_HEX4(0,trace,&q,sizeof(void*));
981 #endif /* QDIO_DBF_LIKE_HELL */
982
983         if (unlikely(qdio_reserve_q(q))) {
984                 qdio_release_q(q);
985 #ifdef QDIO_PERFORMANCE_STATS
986                 o_p_c++;
987 #endif /* QDIO_PERFORMANCE_STATS */
988                 /* as we're sissies, we'll check next time */
989                 if (likely(!atomic_read(&q->is_in_shutdown))) {
990                         qdio_mark_q(q);
991 #ifdef QDIO_DBF_LIKE_HELL
992                         QDIO_DBF_TEXT4(0,trace,"busy,agn");
993 #endif /* QDIO_DBF_LIKE_HELL */
994                 }
995                 return;
996         }
997 #ifdef QDIO_PERFORMANCE_STATS
998         o_p_nc++;
999 #endif /* QDIO_PERFORMANCE_STATS */
1000
1001         /* see comment in qdio_kick_outbound_q */
1002         siga_attempts=atomic_read(&q->busy_siga_counter);
1003         while (siga_attempts) {
1004                 atomic_dec(&q->busy_siga_counter);
1005                 qdio_kick_outbound_q(q);
1006                 siga_attempts--;
1007         }
1008
1009 #ifdef QDIO_PERFORMANCE_STATS
1010         perf_stats.tl_runs++;
1011 #endif /* QDIO_PERFORMANCE_STATS */
1012
1013         if (qdio_has_outbound_q_moved(q)) {
1014                 qdio_kick_outbound_handler(q);
1015         }
1016
1017         if (q->is_iqdio_q) {
1018                 /* for asynchronous queues, we better check, if the fill
1019                  * level is too high. for synchronous queues, the fill
1020                  * level will never be that high. */
1021                 if (atomic_read(&q->number_of_buffers_used)>
1022                     IQDIO_FILL_LEVEL_TO_POLL) {
1023                         qdio_mark_q(q);
1024                 }
1025         } else if (!q->hydra_gives_outbound_pcis) {
1026                 if (!qdio_is_outbound_q_done(q)) {
1027                         qdio_mark_q(q);
1028                 }
1029         }
1030
1031         qdio_release_q(q);
1032 }
1033
1034 static void qdio_outbound_processing(qdio_q_t *q)
1035 {
1036         __qdio_outbound_processing(q);
1037 }
1038
1039 /************************* INBOUND ROUTINES *******************************/
1040
1041
1042 static inline int qdio_get_inbound_buffer_frontier(qdio_q_t *q)
1043 {
1044         int f,f_mod_no;
1045         volatile char *slsb;
1046         char slsbyte;
1047         int first_not_to_check;
1048         char dbf_text[15];
1049 #ifdef QDIO_USE_PROCESSING_STATE
1050         int last_position=-1;
1051 #endif /* QDIO_USE_PROCESSING_STATE */
1052
1053 #ifdef QDIO_DBF_LIKE_HELL
1054         QDIO_DBF_TEXT4(0,trace,"getibfro");
1055         QDIO_DBF_HEX4(0,trace,&q,sizeof(void*));
1056 #endif /* QDIO_DBF_LIKE_HELL */
1057
1058         slsb=&q->slsb.acc.val[0];
1059         f_mod_no=f=q->first_to_check;
1060         /* we don't check 128 buffers, as otherwise qdio_has_inbound_q_moved
1061          * would return 0 */
1062         first_not_to_check=f+qdio_min(atomic_read(&q->number_of_buffers_used),
1063                                       (QDIO_MAX_BUFFERS_PER_Q-1));
1064
1065         /* we don't use this one, as a PCI or we after a thin interrupt
1066          * will sync the queues
1067         SYNC_MEMORY;*/
1068
1069 check_next:
1070         f_mod_no=f&(QDIO_MAX_BUFFERS_PER_Q-1);
1071         if (f==first_not_to_check) goto out;
1072         slsbyte=slsb[f_mod_no];
1073
1074         /* CU_EMPTY means frontier is reached */
1075         if (slsbyte==SLSB_CU_INPUT_EMPTY) {
1076 #ifdef QDIO_DBF_LIKE_HELL
1077                 QDIO_DBF_TEXT5(0,trace,"inptempt");
1078 #endif /* QDIO_DBF_LIKE_HELL */
1079                 goto out;
1080         }
1081
1082         /* P_PRIMED means set slsb to P_PROCESSING and move on */
1083         if (slsbyte==SLSB_P_INPUT_PRIMED) {
1084 #ifdef QDIO_DBF_LIKE_HELL
1085                 QDIO_DBF_TEXT5(0,trace,"inptprim");
1086 #endif /* QDIO_DBF_LIKE_HELL */
1087
1088 #ifdef QDIO_USE_PROCESSING_STATE
1089                 /* as soon as running under VM, polling the input queues will
1090                  * kill VM in terms of CP overhead */
1091                 if (q->siga_sync) {
1092                         set_slsb(&slsb[f_mod_no],SLSB_P_INPUT_NOT_INIT);
1093                 } else {
1094                         /* set the previous buffer to NOT_INIT. The current
1095                          * buffer will be set to PROCESSING at the end of
1096                          * this function to avoid further interrupts. */
1097                         if (last_position>=0)
1098                                 set_slsb(&slsb[last_position],
1099                                         SLSB_P_INPUT_NOT_INIT);
1100                         atomic_set(&q->polling,1);
1101                         last_position=f_mod_no;
1102                 }
1103 #else /* QDIO_USE_PROCESSING_STATE */
1104                 set_slsb(&slsb[f_mod_no],SLSB_P_INPUT_NOT_INIT);
1105 #endif /* QDIO_USE_PROCESSING_STATE */
1106                 /* not needed, as the inbound queue will be synced on the next
1107                  * siga-r
1108                 SYNC_MEMORY;*/
1109                 f++;
1110                 atomic_dec(&q->number_of_buffers_used);
1111                 goto check_next;
1112         }
1113
1114         if ( (slsbyte==SLSB_P_INPUT_NOT_INIT) ||
1115              (slsbyte==SLSB_P_INPUT_PROCESSING) ) {
1116 #ifdef QDIO_DBF_LIKE_HELL
1117                 QDIO_DBF_TEXT5(0,trace,"inpnipro");
1118 #endif /* QDIO_DBF_LIKE_HELL */
1119                 goto out;
1120         }
1121
1122         /* P_ERROR means frontier is reached, break and report error */
1123         if (slsbyte==SLSB_P_INPUT_ERROR) {
1124                 sprintf(dbf_text,"inperr%2x",f_mod_no);
1125                 QDIO_DBF_TEXT3(1,trace,dbf_text);
1126                 QDIO_DBF_HEX2(1,sbal,q->sbal[f_mod_no],256);
1127
1128                 /* kind of process the buffer */
1129                 set_slsb(&slsb[f_mod_no],SLSB_P_INPUT_NOT_INIT);
1130
1131                 if (q->qdio_error)
1132                         q->error_status_flags|=
1133                                 QDIO_STATUS_MORE_THAN_ONE_QDIO_ERROR;
1134                 q->qdio_error=SLSB_P_INPUT_ERROR;
1135                 q->error_status_flags|=QDIO_STATUS_LOOK_FOR_ERROR;
1136
1137                 /* we increment the frontier, as this buffer
1138                  * was processed obviously */
1139                 f_mod_no=(f_mod_no+1)&(QDIO_MAX_BUFFERS_PER_Q-1);
1140                 atomic_dec(&q->number_of_buffers_used);
1141
1142 #ifdef QDIO_USE_PROCESSING_STATE
1143                 last_position=-1;
1144 #endif /* QDIO_USE_PROCESSING_STATE */
1145
1146                 goto out;
1147         }
1148
1149         /* everything else means frontier not changed (HALTED or so) */
1150 out:
1151         q->first_to_check=f_mod_no;
1152
1153 #ifdef QDIO_USE_PROCESSING_STATE
1154         if (last_position>=0)
1155                 set_slsb(&slsb[last_position],SLSB_P_INPUT_PROCESSING);
1156 #endif /* QDIO_USE_PROCESSING_STATE */
1157
1158 #ifdef QDIO_DBF_LIKE_HELL
1159         QDIO_DBF_HEX4(0,trace,&q->first_to_check,sizeof(int));
1160 #endif /* QDIO_DBF_LIKE_HELL */
1161
1162         return q->first_to_check;
1163 }
1164
1165 static inline int qdio_has_inbound_q_moved(qdio_q_t *q)
1166 {
1167         int i;
1168
1169 #ifdef QDIO_PERFORMANCE_STATS
1170         static int old_pcis=0;
1171         static int old_thinints=0;
1172
1173         if ((old_pcis==perf_stats.pcis)&&(old_thinints==perf_stats.thinints))
1174                 perf_stats.start_time_inbound=NOW;
1175         else
1176                 old_pcis=perf_stats.pcis;
1177 #endif /* QDIO_PERFORMANCE_STATS */
1178
1179         i=qdio_get_inbound_buffer_frontier(q);
1180         if ( (i!=GET_SAVED_FRONTIER(q)) ||
1181              (q->error_status_flags&QDIO_STATUS_LOOK_FOR_ERROR) ) {
1182                 SAVE_FRONTIER(q,i);
1183                 if ((!q->siga_sync)&&(!q->hydra_gives_outbound_pcis)) {
1184                         SAVE_TIMESTAMP(q);
1185                 }
1186
1187 #ifdef QDIO_DBF_LIKE_HELL
1188                 QDIO_DBF_TEXT4(0,trace,"inhasmvd");
1189                 QDIO_DBF_HEX4(0,trace,&q,sizeof(void*));
1190 #endif /* QDIO_DBF_LIKE_HELL */
1191                 return 1;
1192         } else {
1193 #ifdef QDIO_DBF_LIKE_HELL
1194                 QDIO_DBF_TEXT4(0,trace,"inhsntmv");
1195                 QDIO_DBF_HEX4(0,trace,&q,sizeof(void*));
1196 #endif /* QDIO_DBF_LIKE_HELL */
1197                 return 0;
1198         }
1199 }
1200
1201 /* means, no more buffers to be filled */
1202 static inline int iqdio_is_inbound_q_done(qdio_q_t *q)
1203 {
1204         int no_used;
1205 #ifdef QDIO_DBF_LIKE_HELL
1206         char dbf_text[15];
1207 #endif /* QDIO_DBF_LIKE_HELL */
1208
1209         no_used=atomic_read(&q->number_of_buffers_used);
1210
1211         /* propagate the change from 82 to 80 through VM */
1212         SYNC_MEMORY;
1213
1214 #ifdef QDIO_DBF_LIKE_HELL
1215         if (no_used) {
1216                 sprintf(dbf_text,"iqisnt%02x",no_used);
1217                 QDIO_DBF_TEXT4(0,trace,dbf_text);
1218         } else {
1219                 QDIO_DBF_TEXT4(0,trace,"iniqisdo");
1220         }
1221         QDIO_DBF_HEX4(0,trace,&q,sizeof(void*));
1222 #endif /* QDIO_DBF_LIKE_HELL */
1223
1224         if (!no_used) {
1225                 return 1;
1226         }
1227
1228         if (q->siga_sync) {
1229                 if (q->slsb.acc.val[q->first_to_check]==SLSB_P_INPUT_PRIMED) {
1230                         /* ok, the next input buffer is primed. that means,
1231                          * that device state change indicator and adapter
1232                          * local summary are set, so we will find it next
1233                          * time.
1234                          * we will return 0 below, as there is nothing to
1235                          * do, except of scheduling ourselves for the next
1236                          * time. */
1237                         tiqdio_set_summary_bit((__u32*)q->dev_st_chg_ind);
1238                         tiqdio_sched_tl();
1239                 } else {
1240                         /* nothing more to do, if next buffer is not PRIMED.
1241                          * note that we did a SYNC_MEMORY before, that there
1242                          * has been a sychnronization.
1243                          * we will return 0 below, as there is nothing to do
1244                          * (stop_polling not necessary, as we have not been
1245                          * using the PROCESSING state */
1246                 }
1247         } else {
1248                 /* we'll check for more primed buffers
1249                  * in qeth_stop_polling */
1250         }
1251
1252         return 0;
1253 }
1254
1255 static inline int qdio_is_inbound_q_done(qdio_q_t *q)
1256 {
1257         int no_used;
1258 #ifdef QDIO_DBF_LIKE_HELL
1259         char dbf_text[15];
1260 #endif /* QDIO_DBF_LIKE_HELL */
1261
1262         no_used=atomic_read(&q->number_of_buffers_used);
1263
1264         /* we need that one for synchronization with the OSA/FCP card, as it
1265          * does a kind of PCI avoidance */
1266         SYNC_MEMORY;
1267
1268         if (!no_used) {
1269 #ifdef QDIO_DBF_LIKE_HELL
1270                 QDIO_DBF_TEXT4(0,trace,"inqisdnA");
1271                 QDIO_DBF_HEX4(0,trace,&q,sizeof(void*));
1272                 QDIO_DBF_TEXT4(0,trace,dbf_text);
1273 #endif /* QDIO_DBF_LIKE_HELL */
1274                 return 1;
1275         }
1276
1277         if (q->slsb.acc.val[q->first_to_check]==SLSB_P_INPUT_PRIMED) {
1278                 /* we got something to do */
1279 #ifdef QDIO_DBF_LIKE_HELL
1280                 QDIO_DBF_TEXT4(0,trace,"inqisntA");
1281                 QDIO_DBF_HEX4(0,trace,&q,sizeof(void*));
1282 #endif /* QDIO_DBF_LIKE_HELL */
1283                 return 0;
1284         }
1285
1286         /* on VM, we don't poll, so the q is always done here */
1287         if (q->siga_sync) return 1;
1288         if (q->hydra_gives_outbound_pcis) return 1;
1289
1290         /* at this point we know, that inbound first_to_check
1291            has (probably) not moved (see qdio_inbound_processing) */
1292         if (NOW>GET_SAVED_TIMESTAMP(q)+q->timing.threshold) {
1293 #ifdef QDIO_DBF_LIKE_HELL
1294                 QDIO_DBF_TEXT4(0,trace,"inqisdon");
1295                 QDIO_DBF_HEX4(0,trace,&q,sizeof(void*));
1296                 sprintf(dbf_text,"pf%02xcn%02x",q->first_to_check,no_used);
1297                 QDIO_DBF_TEXT4(0,trace,dbf_text);
1298 #endif /* QDIO_DBF_LIKE_HELL */
1299                 return 1;
1300         } else {
1301 #ifdef QDIO_DBF_LIKE_HELL
1302                 QDIO_DBF_TEXT4(0,trace,"inqisntd");
1303                 QDIO_DBF_HEX4(0,trace,&q,sizeof(void*));
1304                 sprintf(dbf_text,"pf%02xcn%02x",q->first_to_check,no_used);
1305                 QDIO_DBF_TEXT4(0,trace,dbf_text);
1306 #endif /* QDIO_DBF_LIKE_HELL */
1307                 return 0;
1308         }
1309 }
1310
1311 static inline void qdio_kick_inbound_handler(qdio_q_t *q)
1312 {
1313         int count=0;
1314         int start,end,real_end,i;
1315 #ifdef QDIO_DBF_LIKE_HELL
1316         char dbf_text[15];
1317
1318         QDIO_DBF_TEXT4(0,trace,"kickinh");
1319         QDIO_DBF_HEX4(0,trace,&q,sizeof(void*));
1320 #endif /* QDIO_DBF_LIKE_HELL */
1321
1322         start=q->first_element_to_kick;
1323         real_end=q->first_to_check;
1324         end=(real_end+QDIO_MAX_BUFFERS_PER_Q-1)&(QDIO_MAX_BUFFERS_PER_Q-1);
1325
1326         i=start;
1327         while (1) {
1328                 count++;
1329                 qdio_translate_buffer_back(q,i);
1330                 if (i==end) break;
1331                 i=(i+1)&(QDIO_MAX_BUFFERS_PER_Q-1);
1332         }
1333
1334 #ifdef QDIO_DBF_LIKE_HELL
1335         sprintf(dbf_text,"s=%2xc=%2x",start,count);
1336         QDIO_DBF_TEXT4(0,trace,dbf_text);
1337 #endif /* QDIO_DBF_LIKE_HELL */
1338
1339         if (likely(q->state==QDIO_IRQ_STATE_ACTIVE))
1340                 q->handler(q->irq,
1341                            QDIO_STATUS_INBOUND_INT|q->error_status_flags,
1342                            q->qdio_error,q->siga_error,q->q_no,start,count,
1343                            q->int_parm);
1344
1345         /* for the next time: */
1346         q->first_element_to_kick=real_end;
1347         q->qdio_error=0;
1348         q->siga_error=0;
1349         q->error_status_flags=0;
1350
1351 #ifdef QDIO_PERFORMANCE_STATS
1352         perf_stats.inbound_time+=NOW-perf_stats.start_time_inbound;
1353         perf_stats.inbound_cnt++;
1354 #endif /* QDIO_PERFORMANCE_STATS */
1355 }
1356
1357 static inline void __tiqdio_inbound_processing(qdio_q_t *q,
1358                                                int spare_ind_was_set)
1359 {
1360         qdio_irq_t *irq_ptr;
1361         qdio_q_t *oq;
1362         int i;
1363
1364 #ifdef QDIO_DBF_LIKE_HELL
1365         QDIO_DBF_TEXT4(0,trace,"iqinproc");
1366         QDIO_DBF_HEX4(0,trace,&q,sizeof(void*));
1367 #endif /* QDIO_DBF_LIKE_HELL */
1368
1369         /* we first want to reserve the q, so that we know, that we don't
1370          * interrupt ourselves and call qdio_unmark_q, as is_in_shutdown might
1371          * be set */
1372         if (unlikely(qdio_reserve_q(q))) {
1373                 qdio_release_q(q);
1374 #ifdef QDIO_PERFORMANCE_STATS
1375                 ii_p_c++;
1376 #endif /* QDIO_PERFORMANCE_STATS */
1377                 /* as we might just be about to stop polling, we make
1378                  * sure that we check again at least once more */
1379                 tiqdio_sched_tl();
1380                 return;
1381         }
1382 #ifdef QDIO_PERFORMANCE_STATS
1383         ii_p_nc++;
1384 #endif /* QDIO_PERFORMANCE_STATS */
1385         if (unlikely(atomic_read(&q->is_in_shutdown))) {
1386                 qdio_unmark_q(q);
1387                 goto out;
1388         }
1389
1390         /* we reset spare_ind_was_set, when the queue does not use the
1391          * spare indicator */
1392         if (spare_ind_was_set) {
1393                 spare_ind_was_set==(q->dev_st_chg_ind==&spare_indicator);
1394         }
1395
1396         if ( (*(q->dev_st_chg_ind)) || (spare_ind_was_set) ) {
1397                 /* q->dev_st_chg_ind is the indicator, be it shared or not.
1398                  * only clear it, if indicator is non-shared */
1399                 if (!spare_ind_was_set) {
1400                         tiqdio_clear_summary_bit((__u32*)q->dev_st_chg_ind);
1401                 }
1402
1403                 if (q->hydra_gives_outbound_pcis) {
1404                         if (!q->siga_sync_done_on_thinints) {
1405                                 SYNC_MEMORY_ALL;
1406                         } else if ((!q->siga_sync_done_on_outb_tis)&&
1407                                    (q->hydra_gives_outbound_pcis)) {
1408                                 SYNC_MEMORY_ALL_OUTB;
1409                         }
1410                 } else {
1411                         SYNC_MEMORY;
1412                 }
1413
1414                 /* maybe we have to do work on our outbound queues... at least
1415                  * we have to check for outbound-int-capable thinint-capable
1416                  * queues */
1417                 if (q->hydra_gives_outbound_pcis) {
1418                         irq_ptr=(qdio_irq_t*)q->irq_ptr;
1419                         for (i=0;i<irq_ptr->no_output_qs;i++) {
1420                                 oq=irq_ptr->output_qs[i];
1421 #ifdef QDIO_PERFORMANCE_STATS
1422                                 perf_stats.tl_runs--;
1423 #endif /* QDIO_PERFORMANCE_STATS */
1424                                 if (!qdio_is_outbound_q_done(oq)) {
1425                                         __qdio_outbound_processing(oq);
1426                                 }
1427                         }
1428                 }
1429
1430                 if (qdio_has_inbound_q_moved(q)) {
1431                         qdio_kick_inbound_handler(q);
1432                         if (iqdio_is_inbound_q_done(q)) {
1433                                 if (!qdio_stop_polling(q)) {
1434                                         /* we set the flags to get into
1435                                          * the stuff next time, see also
1436                                          * comment in qdio_stop_polling */
1437                                         tiqdio_set_summary_bit
1438                                                 ((__u32*)q->dev_st_chg_ind);
1439                                         tiqdio_sched_tl();
1440                                 }
1441                         }
1442                 }
1443         }
1444 out:
1445         qdio_release_q(q);
1446 }
1447
1448 static void tiqdio_inbound_processing(qdio_q_t *q)
1449 {
1450         __tiqdio_inbound_processing(q,atomic_read(&spare_indicator_usecount));
1451 }
1452
1453 static inline void __qdio_inbound_processing(qdio_q_t *q)
1454 {
1455         int q_laps=0;
1456
1457 #ifdef QDIO_DBF_LIKE_HELL
1458         QDIO_DBF_TEXT4(0,trace,"qinproc");
1459         QDIO_DBF_HEX4(0,trace,&q,sizeof(void*));
1460 #endif /* QDIO_DBF_LIKE_HELL */
1461
1462         if (unlikely(qdio_reserve_q(q))) {
1463                 qdio_release_q(q);
1464 #ifdef QDIO_PERFORMANCE_STATS
1465                 i_p_c++;
1466 #endif /* QDIO_PERFORMANCE_STATS */
1467                 /* as we're sissies, we'll check next time */
1468                 if (likely(!atomic_read(&q->is_in_shutdown))) {
1469                         qdio_mark_q(q);
1470 #ifdef QDIO_DBF_LIKE_HELL
1471                         QDIO_DBF_TEXT4(0,trace,"busy,agn");
1472 #endif /* QDIO_DBF_LIKE_HELL */
1473                 }
1474                 return;
1475         }
1476 #ifdef QDIO_PERFORMANCE_STATS
1477         i_p_nc++;
1478         perf_stats.tl_runs++;
1479 #endif /* QDIO_PERFORMANCE_STATS */
1480
1481 again:
1482         if (qdio_has_inbound_q_moved(q)) {
1483                 qdio_kick_inbound_handler(q);
1484                 if (!qdio_stop_polling(q)) {
1485                         q_laps++;
1486                         if (q_laps<QDIO_Q_LAPS) goto again;
1487                 }
1488                 qdio_mark_q(q);
1489         } else {
1490                 if (!qdio_is_inbound_q_done(q)) /* means poll time is 
1491                                                    not yet over */
1492                         qdio_mark_q(q);
1493         }
1494
1495         qdio_release_q(q);
1496 }
1497
1498 static void qdio_inbound_processing(qdio_q_t *q)
1499 {
1500         __qdio_inbound_processing(q);
1501 }
1502
1503 /************************* MAIN ROUTINES *******************************/
1504
1505 static inline void tiqdio_inbound_checks(void)
1506 {
1507         qdio_q_t *q;
1508         int spare_ind_was_set=0;
1509 #ifdef QDIO_USE_PROCESSING_STATE
1510         int q_laps=0;
1511 #endif /* QDIO_USE_PROCESSING_STATE */
1512
1513 #ifdef QDIO_DBF_LIKE_HELL
1514         char dbf_text[15];
1515
1516         QDIO_DBF_TEXT4(0,trace,"iqdinbck");
1517 #endif /* QDIO_DBF_LIKE_HELL */
1518
1519 #ifdef QDIO_DBF_LIKE_HELL
1520         QDIO_DBF_TEXT5(0,trace,"iqlocsum");
1521 #endif /* QDIO_DBF_LIKE_HELL */
1522
1523 #ifdef QDIO_USE_PROCESSING_STATE
1524 again:
1525 #endif /* QDIO_USE_PROCESSING_STATE */
1526
1527         /* when the spare indicator is used and set, save that and clear it */
1528         if ( (atomic_read(&spare_indicator_usecount)) && (spare_indicator) ) {
1529                 spare_ind_was_set=1;
1530                 tiqdio_clear_summary_bit((__u32*)&spare_indicator);
1531         }
1532
1533         q=(qdio_q_t*)tiq_list;
1534         /* switch all active queues to processing state */
1535         do {
1536                 if (!q) break;
1537                 __tiqdio_inbound_processing(q,spare_ind_was_set);
1538                 q=(qdio_q_t*)q->list_next;
1539         } while (q!=(qdio_q_t*)tiq_list);
1540
1541         /* switch off all queues' processing state, see comments in
1542          * qdio_get_inbound_buffer_frontier */
1543 #ifdef QDIO_USE_PROCESSING_STATE
1544         q=(qdio_q_t*)tiq_list;
1545         do {
1546                 if (!q) {
1547                         tiqdio_sched_tl();
1548                         break;
1549                 }
1550                 /* under VM, we have not used the PROCESSING state, so no
1551                  * need to stop polling */
1552                 if (q->siga_sync) {
1553                         q=(qdio_q_t*)q->list_next;
1554                         continue;
1555                 }
1556
1557                 if (unlikely(qdio_reserve_q(q))) {
1558                         qdio_release_q(q);
1559 #ifdef QDIO_PERFORMANCE_STATS
1560                         ii_p_c++;
1561 #endif /* QDIO_PERFORMANCE_STATS */
1562                         /* as we might just be about to stop polling, we make
1563                          * sure that we check again at least once more */
1564
1565                         /* sanity -- we'd get here without setting the
1566                          * dev st chg ind */
1567                         tiqdio_set_summary_bit((__u32*)q->dev_st_chg_ind);
1568                         tiqdio_sched_tl();
1569                         break;
1570                 }
1571                 if (!qdio_stop_polling(q)) {
1572                         q_laps++;
1573                         if (q_laps<QDIO_Q_LAPS) {
1574                                 qdio_release_q(q);
1575                                 goto again;
1576                         } else {
1577                                 /* we set the flags to get into the stuff
1578                                  * next time, see also comment in
1579                                  * qdio_stop_polling */
1580                                 tiqdio_set_summary_bit((__u32*)
1581                                                       q->dev_st_chg_ind);
1582                                 tiqdio_sched_tl();
1583                         }
1584                 }
1585                 qdio_release_q(q);
1586                 q=(qdio_q_t*)q->list_next;
1587         } while (q!=(qdio_q_t*)tiq_list);
1588 #endif /* QDIO_USE_PROCESSING_STATE */
1589 }
1590
1591 static void tiqdio_tl(unsigned long data)
1592 {
1593 #ifdef QDIO_DBF_LIKE_HELL
1594         QDIO_DBF_TEXT4(0,trace,"tiqdio_tl");
1595 #endif /* QDIO_DBF_LIKE_HELL */
1596 #ifdef QDIO_PERFORMANCE_STATS
1597         perf_stats.tl_runs++;
1598 #endif /* QDIO_PERFORMANCE_STATS */
1599
1600         tiqdio_inbound_checks();
1601 }
1602
1603 /********************* GENERAL HELPER_ROUTINES ***********************/
1604
1605 static qdio_irq_t *qdio_get_irq_ptr(int irq)
1606 {
1607         qdio_irq_t *irq_ptr;
1608         int bucket=irq&(QDIO_IRQ_BUCKETS-1);
1609
1610         read_lock(&irq_list_lock[bucket]);
1611         irq_ptr=first_irq[bucket];
1612         while (irq_ptr) {
1613                 if (irq_ptr->irq==irq) break;
1614                 irq_ptr=irq_ptr->next;
1615         }
1616         read_unlock(&irq_list_lock[bucket]);
1617         return irq_ptr;
1618 }
1619
1620 static qdio_irq_t *qdio_get_irq_ptr_wolock(int irq)
1621 {
1622         qdio_irq_t *irq_ptr=first_irq[irq&(QDIO_IRQ_BUCKETS-1)];
1623
1624         while (irq_ptr) {
1625                 if (irq_ptr->irq==irq) break;
1626                 irq_ptr=irq_ptr->next;
1627         }
1628         return irq_ptr;
1629 }
1630
1631 /* irq_ptr->irq should be set already! */
1632 static void qdio_insert_irq_ptr(qdio_irq_t *irq_ptr)
1633 {
1634         qdio_irq_t *i_p;
1635         int irq,bucket;
1636
1637         if (!irq_ptr) return;
1638
1639         irq=irq_ptr->irq;
1640         bucket=irq&(QDIO_IRQ_BUCKETS-1);
1641
1642         write_lock(&irq_list_lock[bucket]);
1643
1644         if (irq_ptr==qdio_get_irq_ptr_wolock(irq)) goto out;
1645
1646         if (!first_irq[bucket]) {
1647                 first_irq[bucket]=irq_ptr;
1648         } else {
1649                 i_p=first_irq[bucket];
1650                 while (i_p->next)
1651                         i_p=i_p->next;
1652                 i_p->next=irq_ptr;
1653         }
1654         irq_ptr->next=NULL;
1655 out:
1656         write_unlock(&irq_list_lock[bucket]);
1657 }
1658
1659 static void qdio_remove_irq_ptr(qdio_irq_t *irq_ptr)
1660 {
1661         qdio_irq_t *i_p;
1662         int irq,bucket;
1663
1664         if (!irq_ptr) return;
1665
1666         irq=irq_ptr->irq;
1667         bucket=irq&(QDIO_IRQ_BUCKETS-1);
1668
1669         write_lock(&irq_list_lock[bucket]);
1670
1671         if (!qdio_get_irq_ptr_wolock(irq)) goto out;
1672
1673         if (first_irq[irq&(QDIO_IRQ_BUCKETS-1)]==irq_ptr) {
1674                 first_irq[irq&(QDIO_IRQ_BUCKETS-1)]=irq_ptr->next;
1675         } else {
1676                 for (i_p=first_irq[irq&(QDIO_IRQ_BUCKETS-1)];
1677                      i_p->next!=irq_ptr;i_p=i_p->next);
1678                 i_p->next=irq_ptr->next;
1679         }
1680         irq_ptr->next=NULL;
1681 out:
1682         write_unlock(&irq_list_lock[bucket]);
1683 }
1684
1685 static void qdio_release_irq_memory(qdio_irq_t *irq_ptr)
1686 {
1687         int i,j;
1688         int available;
1689
1690         for (i=0;i<QDIO_MAX_QUEUES_PER_IRQ;i++) {
1691                 if (!irq_ptr->input_qs[i]) goto next;
1692                 available=0;
1693                 if (!irq_ptr->input_qs[i]->is_0copy_sbals_q)
1694                         for (j=0;j<QDIO_MAX_BUFFERS_PER_Q;j++) {
1695                                 if (!available) {
1696                                         if (irq_ptr->input_qs[i]->sbal[j])
1697                                                 kfree((void*)irq_ptr->
1698                                                       input_qs[i]->sbal[j]);
1699                                         available=PAGE_SIZE;
1700                                 }
1701                                 available-=sizeof(sbal_t);
1702                         }
1703                 if (irq_ptr->input_qs[i]->slib)
1704                         kfree(irq_ptr->input_qs[i]->slib);
1705                         kfree(irq_ptr->input_qs[i]);
1706
1707 next:
1708                 if (!irq_ptr->output_qs[i]) continue;
1709                 available=0;
1710                 if (!irq_ptr->output_qs[i]->is_0copy_sbals_q)
1711                         for (j=0;j<QDIO_MAX_BUFFERS_PER_Q;j++) {
1712                                 if (!available) {
1713                                         if (irq_ptr->output_qs[i]->sbal[j])
1714                                                 kfree((void*)irq_ptr->
1715                                                       output_qs[i]->sbal[j]);
1716                                         available=PAGE_SIZE;
1717                                 }
1718                                 available-=sizeof(sbal_t);
1719                         }
1720                 if (irq_ptr->output_qs[i]->slib)
1721                         kfree(irq_ptr->output_qs[i]->slib);
1722                 kfree(irq_ptr->output_qs[i]);
1723
1724         }
1725         kfree(irq_ptr->qdr);
1726         kfree(irq_ptr);
1727 }
1728
1729 static inline void qdio_wakeup(atomic_t *var,qdio_irq_t *irq_ptr)
1730 {
1731         wait_queue_head_t *wait_q;
1732
1733 #ifdef QDIO_DBF_LIKE_HELL
1734         char dbf_text[20];
1735         sprintf(dbf_text,"qwkp%4x",irq_ptr->irq);
1736         QDIO_DBF_TEXT3(0,trace,dbf_text);
1737 #endif /* QDIO_DBF_LIKE_HELL */
1738
1739         atomic_set(var,1);
1740         if ((wait_q=&irq_ptr->wait_q))
1741                 wake_up(wait_q);
1742 }
1743
1744 static int qdio_sleepon(atomic_t *var,int timeout,qdio_irq_t *irq_ptr)
1745 {
1746         __u64 stop;
1747         int retval;
1748         DECLARE_WAITQUEUE (current_wait_q,current);
1749
1750 #ifdef QDIO_DBF_LIKE_HELL
1751         char dbf_text[20];
1752         sprintf(dbf_text,"qslp%4x",irq_ptr->irq);
1753         QDIO_DBF_TEXT3(0,trace,dbf_text);
1754 #endif /* QDIO_DBF_LIKE_HELL */
1755
1756         add_wait_queue(&irq_ptr->wait_q,&current_wait_q);
1757         stop=(qdio_get_micros()>>10)+timeout;
1758         for (;;) {
1759                 set_task_state(current,TASK_INTERRUPTIBLE);
1760                 if (atomic_read(var)) {
1761                         atomic_set(var,0);
1762                         retval=0;
1763                         goto out;
1764                 }
1765                 if (qdio_get_micros()>>10>stop) {
1766 #ifdef QDIO_DBF_LIKE_HELL
1767                         sprintf(dbf_text,"%xtime",irq_ptr->irq);
1768                         QDIO_DBF_TEXT3(0,trace,dbf_text);
1769 #endif /* QDIO_DBF_LIKE_HELL */
1770                         retval=-ETIME;
1771                         goto out;
1772                 }
1773                 schedule_timeout(((stop-(qdio_get_micros()>>10))>>10)*HZ);
1774         }
1775  out:
1776         set_task_state(current,TASK_RUNNING);
1777         remove_wait_queue(&irq_ptr->wait_q,&current_wait_q);
1778         return retval;
1779 }
1780
1781 static void qdio_set_impl_params(qdio_irq_t *irq_ptr,
1782                                  unsigned int qib_param_field_format,
1783                           /* pointer to 128 bytes or NULL, if no param field */
1784                                  unsigned char *qib_param_field,
1785                                  unsigned int no_input_qs,
1786                                  unsigned int no_output_qs,
1787                           /* pointer to no_queues*128 words of data or NULL */
1788                                  unsigned long *input_slib_elements,
1789                                  unsigned long *output_slib_elements)
1790 {
1791         int i,j;
1792
1793         if (!irq_ptr) return;
1794
1795         irq_ptr->qib.pfmt=qib_param_field_format;
1796         if (qib_param_field)
1797                 memcpy(irq_ptr->qib.parm,qib_param_field,
1798                        QDIO_MAX_BUFFERS_PER_Q);
1799
1800         if (input_slib_elements)
1801                 for (i=0;i<no_input_qs;i++) {
1802                         for (j=0;j<QDIO_MAX_BUFFERS_PER_Q;j++)
1803                                 irq_ptr->input_qs[i]->slib->slibe[j].parms=
1804                                         input_slib_elements[
1805                                                 i*QDIO_MAX_BUFFERS_PER_Q+j];
1806                 }
1807         if (output_slib_elements)
1808                 for (i=0;i<no_output_qs;i++) {
1809                         for (j=0;j<QDIO_MAX_BUFFERS_PER_Q;j++)
1810                                 irq_ptr->output_qs[i]->slib->slibe[j].parms=
1811                                         output_slib_elements[
1812                                                 i*QDIO_MAX_BUFFERS_PER_Q+j];
1813                 }
1814 }
1815
1816
1817
1818 static int qdio_alloc_qs(qdio_irq_t *irq_ptr,int no_input_qs,int no_output_qs,
1819                          qdio_handler_t *input_handler,
1820                          qdio_handler_t *output_handler,
1821                          unsigned long int_parm,int q_format,
1822                          unsigned long flags,
1823                          void **inbound_sbals_array,
1824                          void **outbound_sbals_array)
1825 {
1826         qdio_q_t *q;
1827         int i,j,result=0;
1828         char dbf_text[20]; /* see qdio_initialize */
1829         void *ptr;
1830         int available;
1831
1832         for (i=0;i<no_input_qs;i++) {
1833                 q=kmalloc(sizeof(qdio_q_t),GFP_KERNEL);
1834
1835                 if (!q) {
1836                         QDIO_PRINT_ERR("kmalloc of q failed!\n");
1837                         goto out;
1838                 }
1839                 memset(q,0,sizeof(qdio_q_t));
1840
1841                 sprintf(dbf_text,"in-q%4x",i);
1842                 QDIO_DBF_TEXT0(0,setup,dbf_text);
1843                 QDIO_DBF_HEX0(0,setup,&q,sizeof(void*));
1844
1845                 q->slib=kmalloc(PAGE_SIZE,GFP_KERNEL);
1846                 if (!q->slib) {
1847                         QDIO_PRINT_ERR("kmalloc of slib failed!\n");
1848                         goto out;
1849                 }
1850                 memset(q->slib,0,PAGE_SIZE);
1851                 q->sl=(sl_t*)(((char*)q->slib)+PAGE_SIZE/2);
1852
1853                 available=0;
1854                 if (flags&QDIO_INBOUND_0COPY_SBALS) {
1855                         for (j=0;j<QDIO_MAX_BUFFERS_PER_Q;j++) {
1856                                 q->sbal[j]=*(inbound_sbals_array++);
1857                         }
1858                 } else for (j=0;j<QDIO_MAX_BUFFERS_PER_Q;j++) {
1859                         if (!available) {
1860                                 q->sbal[j]=kmalloc(PAGE_SIZE,GFP_KERNEL);
1861                                 if (!q->sbal[j]) {
1862                                         goto out;
1863                                 }
1864                                 available=PAGE_SIZE;
1865                                 memset((void*)q->sbal[j],0,PAGE_SIZE);
1866                         } else {
1867                                 q->sbal[j]=(volatile sbal_t *)
1868                                         (((char*)q->sbal[j-1])+sizeof(sbal_t));
1869                         }
1870                         available-=sizeof(sbal_t);
1871                 }
1872
1873                 q->queue_type=q_format;
1874                 q->int_parm=int_parm;
1875                 irq_ptr->input_qs[i]=q;
1876                 q->irq=irq_ptr->irq;
1877                 q->irq_ptr=irq_ptr;
1878                 q->mask=1<<(31-i);
1879                 q->q_no=i;
1880                 q->is_input_q=1;
1881                 q->is_0copy_sbals_q=flags&QDIO_INBOUND_0COPY_SBALS;
1882                 q->first_to_check=0;
1883                 q->last_move_ftc=0;
1884                 q->handler=input_handler;
1885                 q->dev_st_chg_ind=irq_ptr->dev_st_chg_ind;
1886
1887                 q->tasklet.data=(unsigned long)q;
1888                 /* q->is_thinint_q isn't valid at this time, but
1889                  * irq_ptr->is_thinint_irq is */
1890                 q->tasklet.func=(void(*)(unsigned long))
1891                         ((irq_ptr->is_thinint_irq)?&tiqdio_inbound_processing:
1892                          &qdio_inbound_processing);
1893
1894                 /* actually this is not used for inbound queues. yet. */
1895                 atomic_set(&q->busy_siga_counter,0);
1896                 q->timing.busy_start=0;
1897
1898 /*              for (j=0;j<QDIO_STATS_NUMBER;j++)
1899                         q->timing.last_transfer_times[j]=(qdio_get_micros()/
1900                                                           QDIO_STATS_NUMBER)*j;
1901                 q->timing.last_transfer_index=QDIO_STATS_NUMBER-1;
1902 */
1903
1904                 /* fill in slib */
1905                 if (i>0) irq_ptr->input_qs[i-1]->slib->nsliba=
1906                                  QDIO_PFIX_GET_ADDR(q->slib);
1907                 q->slib->sla=QDIO_PFIX_GET_ADDR(q->sl);
1908                 q->slib->slsba=QDIO_PFIX_GET_ADDR((void *)&q->slsb.acc.val[0]);
1909
1910                 /* fill in sl */
1911                 for (j=0;j<QDIO_MAX_BUFFERS_PER_Q;j++)
1912                         q->sl->element[j].sbal=
1913                                 QDIO_PFIX_GET_ADDR((void *)q->sbal[j]);
1914
1915                 QDIO_DBF_TEXT2(0,setup,"sl-sb-b0");
1916                 ptr=(void*)q->sl;
1917                 QDIO_DBF_HEX2(0,setup,&ptr,sizeof(void*));
1918                 ptr=(void*)&q->slsb;
1919                 QDIO_DBF_HEX2(0,setup,&ptr,sizeof(void*));
1920                 ptr=(void*)q->sbal[0];
1921                 QDIO_DBF_HEX2(0,setup,&ptr,sizeof(void*));
1922
1923                 /* fill in slsb */
1924                 for (j=0;j<QDIO_MAX_BUFFERS_PER_Q;j++) {
1925                         set_slsb(&q->slsb.acc.val[j],
1926                                  SLSB_P_INPUT_NOT_INIT);
1927                         q->sbal[j]->element[1].sbalf.i1.key=
1928                                 QDIO_STORAGE_ACC_KEY;
1929                 }
1930         }
1931
1932         for (i=0;i<no_output_qs;i++) {
1933                 q=kmalloc(sizeof(qdio_q_t),GFP_KERNEL);
1934
1935                 if (!q) {
1936                         goto out;
1937                 }
1938                 memset(q,0,sizeof(qdio_q_t));
1939
1940                 sprintf(dbf_text,"outq%4x",i);
1941                 QDIO_DBF_TEXT0(0,setup,dbf_text);
1942                 QDIO_DBF_HEX0(0,setup,&q,sizeof(void*));
1943
1944                 q->slib=kmalloc(PAGE_SIZE,GFP_KERNEL);
1945                 if (!q->slib) {
1946                         QDIO_PRINT_ERR("kmalloc of slib failed!\n");
1947                         goto out;
1948                 }
1949                 memset(q->slib,0,PAGE_SIZE);
1950                 q->sl=(sl_t*)(((char*)q->slib)+PAGE_SIZE/2);
1951
1952                 available=0;
1953                 if (flags&QDIO_OUTBOUND_0COPY_SBALS) {
1954                         for (j=0;j<QDIO_MAX_BUFFERS_PER_Q;j++) {
1955                                 q->sbal[j]=*(outbound_sbals_array++);
1956                         }
1957                 } else for (j=0;j<QDIO_MAX_BUFFERS_PER_Q;j++) {
1958                         if (!available) {
1959                                 q->sbal[j]=kmalloc(PAGE_SIZE,GFP_KERNEL);
1960                                 if (!q->sbal[j]) {
1961                                         goto out;
1962                                 }
1963                                 available=PAGE_SIZE;
1964                                 memset((void*)q->sbal[j],0,PAGE_SIZE);
1965                         } else {
1966                                 q->sbal[j]=(volatile sbal_t *)
1967                                         (((char*)q->sbal[j-1])+sizeof(sbal_t));
1968                         }
1969                         available-=sizeof(sbal_t);
1970                 }
1971
1972                 q->queue_type=q_format;
1973                 q->int_parm=int_parm;
1974                 irq_ptr->output_qs[i]=q;
1975                 q->is_input_q=0;
1976                 q->is_0copy_sbals_q=flags&QDIO_OUTBOUND_0COPY_SBALS;
1977                 q->irq=irq_ptr->irq;
1978                 q->irq_ptr=irq_ptr;
1979                 q->mask=1<<(31-i);
1980                 q->q_no=i;
1981                 q->first_to_check=0;
1982                 q->last_move_ftc=0;
1983                 q->handler=output_handler;
1984
1985                 q->tasklet.data=(unsigned long)q;
1986                 q->tasklet.func=(void(*)(unsigned long))
1987                         &qdio_outbound_processing;
1988
1989                 atomic_set(&q->busy_siga_counter,0);
1990                 q->timing.busy_start=0;
1991
1992                 /* fill in slib */
1993                 if (i>0) irq_ptr->output_qs[i-1]->slib->nsliba=
1994                                  QDIO_PFIX_GET_ADDR(q->slib);
1995                 q->slib->sla=QDIO_PFIX_GET_ADDR(q->sl);
1996                 q->slib->slsba=QDIO_PFIX_GET_ADDR((void *)&q->slsb.acc.val[0]);
1997
1998                 /* fill in sl */
1999                 for (j=0;j<QDIO_MAX_BUFFERS_PER_Q;j++)
2000                         q->sl->element[j].sbal=
2001                                 QDIO_PFIX_GET_ADDR((void *)q->sbal[j]);
2002
2003                 QDIO_DBF_TEXT2(0,setup,"sl-sb-b0");
2004                 ptr=(void*)q->sl;
2005                 QDIO_DBF_HEX2(0,setup,&ptr,sizeof(void*));
2006                 ptr=(void*)&q->slsb;
2007                 QDIO_DBF_HEX2(0,setup,&ptr,sizeof(void*));
2008                 ptr=(void*)q->sbal[0];
2009                 QDIO_DBF_HEX2(0,setup,&ptr,sizeof(void*));
2010
2011                 /* fill in slsb */
2012                 for (j=0;j<QDIO_MAX_BUFFERS_PER_Q;j++) {
2013                         set_slsb(&q->slsb.acc.val[j],
2014                                  SLSB_P_OUTPUT_NOT_INIT);
2015                         q->sbal[j]->element[1].sbalf.i1.key=
2016                                 QDIO_STORAGE_ACC_KEY;
2017                 }
2018         }
2019
2020         result=1;
2021 out:
2022         return result;
2023 }
2024
2025 static void qdio_fill_thresholds(qdio_irq_t *irq_ptr,
2026                                  unsigned int no_input_qs,
2027                                  unsigned int no_output_qs,
2028                                  unsigned int min_input_threshold,
2029                                  unsigned int max_input_threshold,
2030                                  unsigned int min_output_threshold,
2031                                  unsigned int max_output_threshold)
2032 {
2033         int i;
2034         qdio_q_t *q;
2035
2036         for (i=0;i<no_input_qs;i++) {
2037                 q=irq_ptr->input_qs[i];
2038                 q->timing.threshold=max_input_threshold;
2039 /*              for (j=0;j<QDIO_STATS_CLASSES;j++) {
2040                         q->threshold_classes[j].threshold=
2041                                 min_input_threshold+
2042                                 (max_input_threshold-min_input_threshold)/
2043                                 QDIO_STATS_CLASSES;
2044                 }
2045                 qdio_use_thresholds(q,QDIO_STATS_CLASSES/2);*/
2046         }
2047         for (i=0;i<no_output_qs;i++) {
2048                 q=irq_ptr->output_qs[i];
2049                 q->timing.threshold=max_output_threshold;
2050 /*              for (j=0;j<QDIO_STATS_CLASSES;j++) {
2051                         q->threshold_classes[j].threshold=
2052                                 min_output_threshold+
2053                                 (max_output_threshold-min_output_threshold)/
2054                                 QDIO_STATS_CLASSES;
2055                 }
2056                 qdio_use_thresholds(q,QDIO_STATS_CLASSES/2);*/
2057         }
2058 }
2059
2060 static int tiqdio_thinint_handler(__u32 intparm)
2061 {
2062 #ifdef QDIO_DBF_LIKE_HELL
2063         QDIO_DBF_TEXT4(0,trace,"thin_int");
2064 #endif /* QDIO_DBF_LIKE_HELL */
2065
2066 #ifdef QDIO_PERFORMANCE_STATS
2067         perf_stats.thinints++;
2068         perf_stats.start_time_inbound=NOW;
2069 #endif /* QDIO_PERFORMANCE_STATS */
2070
2071         /* SVS only when needed:
2072          * issue SVS to benefit from iqdio interrupt avoidance
2073          * (SVS clears AISOI)*/
2074         if (!omit_svs) {
2075                 tiqdio_clear_global_summary();
2076         }
2077
2078         tiqdio_inbound_checks();
2079         return 0;
2080 }
2081
2082 static void qdio_set_state(qdio_irq_t *irq_ptr,int state)
2083 {
2084         int i;
2085         char dbf_text[15];
2086
2087         QDIO_DBF_TEXT5(0,trace,"newstate");
2088         sprintf(dbf_text,"%4x%4x",irq_ptr->irq,state);
2089         QDIO_DBF_TEXT5(0,trace,dbf_text);
2090
2091         irq_ptr->state=state;
2092         for (i=0;i<irq_ptr->no_input_qs;i++)
2093                 irq_ptr->input_qs[i]->state=state;
2094         for (i=0;i<irq_ptr->no_output_qs;i++)
2095                 irq_ptr->output_qs[i]->state=state;
2096         mb();
2097 }
2098
2099 static void qdio_handler(int irq,devstat_t *devstat,struct pt_regs *p)
2100 {
2101         qdio_irq_t *irq_ptr;
2102         qdio_q_t *q;
2103         int i;
2104         int cstat,dstat;
2105         int rqparam;
2106         char dbf_text[15]="qintXXXX";
2107
2108         cstat = devstat->cstat;
2109         dstat = devstat->dstat;
2110         rqparam=devstat->intparm;
2111
2112         *((int*)(&dbf_text[4]))=irq;
2113         QDIO_DBF_HEX4(0,trace,dbf_text,QDIO_DBF_TRACE_LEN);
2114         
2115         if (!rqparam) {
2116                 QDIO_PRINT_STUPID("got unsolicited interrupt in qdio " \
2117                                   "handler, irq 0x%x\n",irq);
2118                 return;
2119         }
2120
2121         irq_ptr=qdio_get_irq_ptr(irq);
2122         if (!irq_ptr) {
2123                 sprintf(dbf_text,"uint%4x",irq);
2124                 QDIO_DBF_TEXT2(1,trace,dbf_text);
2125                 QDIO_PRINT_ERR("received interrupt on unused irq 0x%04x!\n",
2126                                irq);
2127                 return;
2128         }
2129
2130         if (devstat->flag&DEVSTAT_FLAG_SENSE_AVAIL) {
2131                 sprintf(dbf_text,"sens%4x",irq);
2132                 QDIO_DBF_TEXT2(1,trace,dbf_text);
2133                 QDIO_DBF_HEX0(0,sense,&devstat->ii.irb,QDIO_DBF_SENSE_LEN);
2134
2135                 QDIO_PRINT_WARN("sense data available on qdio channel.\n");
2136                 HEXDUMP16(WARN,"irb: ",&devstat->ii.irb);
2137                 HEXDUMP16(WARN,"sense data: ",&devstat->ii.sense.data[0]);
2138         }
2139
2140         irq_ptr->io_result_cstat=ioinfo[irq]->devstat.cstat;
2141         irq_ptr->io_result_dstat=ioinfo[irq]->devstat.dstat;
2142         irq_ptr->io_result_flags=ioinfo[irq]->devstat.flag;
2143
2144         if ( (rqparam==QDIO_DOING_ACTIVATE) &&
2145              (cstat & SCHN_STAT_PCI) ) {
2146 #ifdef QDIO_PERFORMANCE_STATS
2147                 perf_stats.pcis++;
2148                 perf_stats.start_time_inbound=NOW;
2149 #endif /* QDIO_PERFORMANCE_STATS */
2150                 for (i=0;i<irq_ptr->no_input_qs;i++) {
2151                         q=irq_ptr->input_qs[i];
2152                         if (q->is_input_q&QDIO_FLAG_NO_INPUT_INTERRUPT_CONTEXT)
2153                                 qdio_mark_q(q);
2154                         else {
2155 #ifdef QDIO_PERFORMANCE_STATS
2156                                 perf_stats.tl_runs--;
2157 #endif /* QDIO_PERFORMANCE_STATS */
2158                                 __qdio_inbound_processing(q);
2159                         }
2160                 }
2161                 if (irq_ptr->hydra_gives_outbound_pcis) {
2162                         for (i=0;i<irq_ptr->no_output_qs;i++) {
2163                                 q=irq_ptr->output_qs[i];
2164 #ifdef QDIO_PERFORMANCE_STATS
2165                                 perf_stats.tl_runs--;
2166 #endif /* QDIO_PERFORMANCE_STATS */
2167                                 if (!qdio_is_outbound_q_done(q)) {
2168                                         if (!irq_ptr->sync_done_on_outb_pcis) {
2169                                                 SYNC_MEMORY;
2170                                         }
2171                                         __qdio_outbound_processing(q);
2172                                 }
2173                         }
2174                 }
2175                 return;
2176         }
2177
2178         if ( (rqparam==QDIO_DOING_ACTIVATE) &&
2179              (!cstat) &&
2180              (!dstat) ) {
2181                 rqparam=QDIO_DOING_CLEANUP;
2182         }
2183
2184         if ( (rqparam==QDIO_DOING_ESTABLISH) &&
2185              ( (cstat) ||
2186                (dstat & ~(DEV_STAT_CHN_END|DEV_STAT_DEV_END)) ) ) {
2187                 sprintf(dbf_text,"ick1%4x",irq);
2188                 QDIO_DBF_TEXT2(1,trace,dbf_text);
2189                 QDIO_DBF_HEX2(0,trace,&rqparam,sizeof(int));
2190                 QDIO_DBF_HEX2(0,trace,&dstat,sizeof(int));
2191                 QDIO_DBF_HEX2(0,trace,&cstat,sizeof(int));
2192                 QDIO_PRINT_ERR("received check condition on establish " \
2193                                "queues on irq 0x%x (cs=x%x, ds=x%x).\n",
2194                                irq,cstat,dstat);
2195                 qdio_set_state(irq_ptr,QDIO_IRQ_STATE_STOPPED);
2196                 return;
2197         }
2198
2199         if ( ( (rqparam==QDIO_DOING_ACTIVATE) &&
2200                (dstat==(DEV_STAT_CHN_END|DEV_STAT_DEV_END)) ) ||
2201              ( (rqparam==QDIO_DOING_CLEANUP) || (!rqparam) ) ) {
2202                 qdio_wakeup(&irq_ptr->interrupt_has_been_cleaned,irq_ptr);
2203                 return;
2204         }
2205
2206         if ( (rqparam==QDIO_DOING_ACTIVATE) &&
2207              ( (cstat & ~SCHN_STAT_PCI) ||
2208                (dstat) ) ) {
2209                 sprintf(dbf_text,"ick2%4x",irq);
2210                 QDIO_DBF_TEXT2(1,trace,dbf_text);
2211                 QDIO_DBF_HEX2(0,trace,&rqparam,sizeof(int));
2212                 QDIO_DBF_HEX2(0,trace,&dstat,sizeof(int));
2213                 QDIO_DBF_HEX2(0,trace,&cstat,sizeof(int));
2214                 QDIO_PRINT_ERR("received check condition on activate " \
2215                                "queues on irq 0x%x (cs=x%x, ds=x%x).\n",
2216                                irq,cstat,dstat);
2217                 if (irq_ptr->no_input_qs) {
2218                         q=irq_ptr->input_qs[0];
2219                 } else if (irq_ptr->no_output_qs) {
2220                         q=irq_ptr->output_qs[0];
2221                 } else {
2222                         QDIO_PRINT_ERR("oops... no queue registered on irq " \
2223                                   "0x%x!?\n",irq);
2224                         goto omit_handler_call;
2225                 }
2226                 q->handler(q->irq,QDIO_STATUS_ACTIVATE_CHECK_CONDITION|
2227                            QDIO_STATUS_LOOK_FOR_ERROR,
2228                            0,0,0,-1,-1,q->int_parm);
2229         omit_handler_call:
2230                 qdio_set_state(irq_ptr,QDIO_IRQ_STATE_STOPPED);
2231                 return;
2232         }
2233
2234         qdio_wakeup(&irq_ptr->interrupt_has_arrived,irq_ptr);
2235 }
2236
2237 /* this is for mp3 */
2238 int qdio_synchronize(int irq,unsigned int flags,
2239                      unsigned int queue_number)
2240 {
2241         unsigned int gpr2,gpr3;
2242         int cc;
2243         qdio_q_t *q;
2244         qdio_irq_t *irq_ptr;
2245         char dbf_text[15]="SyncXXXX";
2246         void *ptr;
2247
2248         *((int*)(&dbf_text[4]))=irq;
2249         QDIO_DBF_HEX4(0,trace,dbf_text,QDIO_DBF_TRACE_LEN);
2250         *((int*)(&dbf_text[0]))=flags;
2251         *((int*)(&dbf_text[4]))=queue_number;
2252         QDIO_DBF_HEX4(0,trace,dbf_text,QDIO_DBF_TRACE_LEN);
2253
2254         irq_ptr=qdio_get_irq_ptr(irq);
2255         if (!irq_ptr) return -ENODEV;
2256
2257         if (flags&QDIO_FLAG_SYNC_INPUT) {
2258                 q=irq_ptr->input_qs[queue_number];
2259                 if (!q) return -EINVAL;
2260
2261                 gpr2=0;
2262                 gpr3=q->mask;
2263         } else if (flags&QDIO_FLAG_SYNC_OUTPUT) {
2264                 q=irq_ptr->output_qs[queue_number];
2265                 if (!q) return -EINVAL;
2266
2267                 gpr2=q->mask;
2268                 gpr3=0;
2269         } else return -EINVAL;
2270
2271 #ifdef QDIO_32_BIT
2272         asm volatile (
2273                 "lhi    0,2     \n\t"
2274                 "lr     1,%1    \n\t"
2275                 "lr     2,%2    \n\t"
2276                 "lr     3,%3    \n\t"
2277                 "siga   0       \n\t"
2278                 "ipm    %0      \n\t"
2279                 "srl    %0,28   \n\t"
2280                 : "=d" (cc)
2281                 : "d" (0x10000|q->irq), "d" (gpr2), "d" (gpr3)
2282                 : "cc", "0", "1", "2", "3"
2283                 );
2284 #else /* QDIO_32_BIT */
2285         asm volatile (
2286                 "lghi   0,2     \n\t"
2287                 "llgfr  1,%1    \n\t"
2288                 "llgfr  2,%2    \n\t"
2289                 "llgfr  3,%3    \n\t"
2290                 "siga   0       \n\t"
2291                 "ipm    %0      \n\t"
2292                 "srl    %0,28   \n\t"
2293                 : "=d" (cc)
2294                 : "d" (0x10000|q->irq), "d" (gpr2), "d" (gpr3)
2295                 : "cc", "0", "1", "2", "3"
2296                 );
2297 #endif /* QDIO_32_BIT */
2298
2299         ptr=&cc;
2300         if (cc) QDIO_DBF_HEX3(0,trace,&ptr,sizeof(int));
2301
2302         return cc;
2303 }
2304
2305 unsigned char qdio_get_slsb_state(int irq,unsigned int flag,
2306                                   unsigned int queue_number,
2307                                   unsigned int qidx)
2308 {
2309         qdio_irq_t *irq_ptr;
2310         qdio_q_t *q;
2311
2312         irq_ptr=qdio_get_irq_ptr(irq);
2313         if (!irq_ptr) return SLSB_ERROR_DURING_LOOKUP;
2314
2315         if (flag&QDIO_FLAG_SYNC_INPUT) {
2316                 q=irq_ptr->input_qs[queue_number];
2317         } else if (flag&QDIO_FLAG_SYNC_OUTPUT) {
2318                 q=irq_ptr->output_qs[queue_number];
2319         } else return SLSB_ERROR_DURING_LOOKUP;
2320
2321         return q->slsb.acc.val[qidx&(QDIO_MAX_BUFFERS_PER_Q-1)];
2322 }
2323
2324 static int qdio_chsc(qdio_chsc_area_t *chsc_area)
2325 {
2326         int cc;
2327
2328 #ifdef QDIO_32_BIT
2329         asm volatile (
2330                 ".insn  rre,0xb25f0000,%1,0     \n\t"
2331                 "ipm    %0      \n\t"
2332                 "srl    %0,28   \n\t"
2333                 : "=d" (cc) : "d" (chsc_area) : "cc"
2334                 );
2335 #else /* QDIO_32_BIT */
2336         asm volatile (
2337                 ".insn  rre,0xb25f0000,%1,0     \n\t"
2338                 "ipm    %0      \n\t"
2339                 "srl    %0,28   \n\t"
2340                 : "=d" (cc) : "d" (chsc_area) : "cc"
2341                 );
2342 #endif /* QDIO_32_BIT */
2343
2344         return cc;
2345 }
2346
2347 static unsigned char qdio_check_siga_needs(int sch)
2348 {
2349         int resp_code,result;
2350         unsigned long flags;
2351
2352         spin_lock_irqsave(&chsc_area_lock,flags);
2353
2354         memset(chsc_area,0,sizeof(qdio_chsc_area_t));
2355         chsc_area->request_block.command_code1=0x0010; /* length */
2356         chsc_area->request_block.command_code2=0x0024; /* op code */
2357         chsc_area->request_block.first_sch=sch;
2358         chsc_area->request_block.last_sch=sch;
2359
2360         result=qdio_chsc(chsc_area);
2361
2362         if (result) {
2363                 QDIO_PRINT_WARN("CHSC returned cc %i. Using all " \
2364                                 "SIGAs for sch x%x.\n",
2365                                 result,sch);
2366                 result=-1; /* all flags set */
2367                 goto out;
2368         }
2369
2370         resp_code=chsc_area->request_block.operation_data_area.
2371                 store_qdio_data_response.response_code;
2372         if (resp_code!=QDIO_CHSC_RESPONSE_CODE_OK) {
2373                 QDIO_PRINT_WARN("response upon checking SIGA needs " \
2374                                 "is 0x%x. Using all SIGAs for sch x%x.\n",
2375                                 resp_code,sch);
2376                 result=-1; /* all flags set */
2377                 goto out;
2378         }
2379         if (
2380             (!(chsc_area->request_block.operation_data_area.
2381                store_qdio_data_response.flags&CHSC_FLAG_QDIO_CAPABILITY)) ||
2382             (!(chsc_area->request_block.operation_data_area.
2383                store_qdio_data_response.flags&CHSC_FLAG_VALIDITY)) ||
2384             (chsc_area->request_block.operation_data_area.
2385              store_qdio_data_response.sch!=sch)
2386             ) {
2387                 QDIO_PRINT_WARN("huh? problems checking out sch x%x... " \
2388                                 "using all SIGAs.\n",sch);
2389                 result=CHSC_FLAG_SIGA_INPUT_NECESSARY |
2390                         CHSC_FLAG_SIGA_OUTPUT_NECESSARY |
2391                         CHSC_FLAG_SIGA_SYNC_NECESSARY; /* worst case */
2392                 goto out;
2393         }
2394
2395         result=chsc_area->request_block.operation_data_area.
2396                 store_qdio_data_response.qdioac;
2397 out:
2398         spin_unlock_irqrestore(&chsc_area_lock,flags);
2399         return result;
2400 }
2401
2402 static void qdio_check_for_machine_features(void)
2403 {
2404         int i,result;
2405         unsigned long flags;
2406
2407         spin_lock_irqsave(&chsc_area_lock,flags);
2408
2409         memset(chsc_area,0,sizeof(qdio_chsc_area_t));
2410         chsc_area->request_block.command_code1=0x0010;
2411         chsc_area->request_block.command_code2=0x0010;
2412         result=qdio_chsc(chsc_area);
2413
2414         if (result) {
2415                 QDIO_PRINT_WARN("CHSC returned cc %i. Won't use adapter " \
2416                                 "interrupts for any QDIO device.\n",result);
2417                 result=0;
2418                 goto out;
2419         }
2420
2421         i=chsc_area->request_block.operation_data_area.
2422                 store_qdio_data_response.response_code;
2423         if (i!=1) {
2424                 QDIO_PRINT_WARN("Was not able to determine general " \
2425                                 "characteristics of all QDIO devices " \
2426                                 "aboard.\n");
2427                 result=0;
2428                 goto out;
2429         }
2430
2431         /* 4: request block
2432          * 2: general char
2433          * 512: chsc char */
2434         /* check for bit 67 */
2435         if ( (*(((unsigned int*)(chsc_area))+4+2+2)&0x10000000)!=0x10000000) {
2436                 hydra_thinints=0;
2437         } else {
2438                 hydra_thinints=1;
2439         }
2440
2441         /* check for bit 56: if aif time delay disablement fac installed,
2442          * omit svs even under lpar (good point by rick again) */
2443         if ( (*(((unsigned int*)(chsc_area))+4+2+1)&0x00000080)!=0x00000080) {
2444                 omit_svs=1;
2445         } else {
2446                 omit_svs=0;
2447         }
2448 out:
2449         spin_unlock_irqrestore(&chsc_area_lock,flags);
2450 }
2451
2452 /* the chsc_area is locked by the lock in qdio_activate */
2453 static unsigned int tiqdio_check_chsc_availability(void) {
2454         int result;
2455         int i;
2456         unsigned long flags;
2457
2458         spin_lock_irqsave(&chsc_area_lock,flags);
2459
2460         memset(chsc_area,0,sizeof(qdio_chsc_area_t));
2461         chsc_area->request_block.command_code1=0x0010;
2462         chsc_area->request_block.command_code2=0x0010;
2463         result=qdio_chsc(chsc_area);
2464         if (result) {
2465                 QDIO_PRINT_WARN("Was not able to determine " \
2466                                 "available CHSCs, cc=%i.\n",
2467                                 result);
2468                 result=-EIO;
2469                 goto exit;
2470         }
2471         result=0;
2472         i=chsc_area->request_block.operation_data_area.
2473                 store_qdio_data_response.response_code;
2474         if (i!=1) {
2475                 QDIO_PRINT_WARN("Was not able to determine " \
2476                                 "available CHSCs.\n");
2477                 result=-EIO;
2478                 goto exit;
2479         }
2480         /* 4: request block
2481          * 2: general char
2482          * 512: chsc char */
2483         /* check for bit 41 */
2484         if ( (*(((unsigned int*)(chsc_area))+4+2+1)&0x00400000)!=0x00400000) {
2485                 QDIO_PRINT_WARN("Adapter interruption facility not " \
2486                                 "installed.\n");
2487                 result=-ENOENT;
2488                 goto exit;
2489         }
2490         /* check for bits 107 and 108 */
2491         if ( (*(((unsigned int*)(chsc_area))+4+512+3)&0x00180000)!=
2492              0x00180000 ) {
2493                 QDIO_PRINT_WARN("Set Chan Subsys. Char. & Fast-CHSCs " \
2494                                 "not available.\n");
2495                 result=-ENOENT;
2496                 goto exit;
2497         }
2498 exit:
2499         spin_unlock_irqrestore(&chsc_area_lock,flags);
2500         return result;
2501 }
2502
2503 /* the chsc_area is locked by the lock in qdio_activate */
2504 static unsigned int tiqdio_set_subchannel_ind(qdio_irq_t *irq_ptr,
2505                                              int reset_to_zero)
2506 {
2507         unsigned long real_addr_local_summary_bit;
2508         unsigned long real_addr_dev_st_chg_ind;
2509         void *ptr;
2510         unsigned long flags;
2511         char dbf_text[15];
2512
2513         unsigned int resp_code;
2514         int result;
2515
2516         if (!irq_ptr->is_thinint_irq) return -ENODEV;
2517
2518         if (reset_to_zero) {
2519                 real_addr_local_summary_bit=0;
2520                 real_addr_dev_st_chg_ind=0;
2521         } else {
2522                 real_addr_local_summary_bit=
2523                         virt_to_phys((volatile void *)indicators);
2524                 real_addr_dev_st_chg_ind=
2525                         virt_to_phys((volatile void *)irq_ptr->dev_st_chg_ind);
2526         }
2527
2528         spin_lock_irqsave(&chsc_area_lock,flags);
2529
2530         memset(chsc_area,0,sizeof(qdio_chsc_area_t));
2531         chsc_area->request_block.command_code1=0x0fe0;
2532         chsc_area->request_block.command_code2=0x0021;
2533         chsc_area->request_block.operation_code=0;
2534         chsc_area->request_block.image_id=0;
2535
2536         chsc_area->request_block.operation_data_area.set_chsc.
2537                 summary_indicator_addr=real_addr_local_summary_bit;
2538         chsc_area->request_block.operation_data_area.set_chsc.
2539                 subchannel_indicator_addr=real_addr_dev_st_chg_ind;
2540         chsc_area->request_block.operation_data_area.set_chsc.
2541                 ks=QDIO_STORAGE_ACC_KEY;
2542         chsc_area->request_block.operation_data_area.set_chsc.
2543                 kc=QDIO_STORAGE_ACC_KEY;
2544         chsc_area->request_block.operation_data_area.set_chsc.
2545                 isc=TIQDIO_THININT_ISC;
2546         chsc_area->request_block.operation_data_area.set_chsc.
2547                 subsystem_id=(1<<16)+irq_ptr->irq;
2548
2549         result=qdio_chsc(chsc_area);
2550         if (result) {
2551                 QDIO_PRINT_WARN("could not set indicators on irq x%x, " \
2552                                 "cc=%i.\n",irq_ptr->irq,result);
2553                 result=-EIO;
2554                 goto out;
2555         }
2556
2557         resp_code=chsc_area->response_block.response_code;
2558         if (resp_code!=QDIO_CHSC_RESPONSE_CODE_OK) {
2559                 QDIO_PRINT_WARN("response upon setting indicators " \
2560                                 "is 0x%x.\n",resp_code);
2561                 sprintf(dbf_text,"sidR%4x",resp_code);
2562                 QDIO_DBF_TEXT1(0,trace,dbf_text);
2563                 QDIO_DBF_TEXT1(0,setup,dbf_text);
2564                 ptr=&chsc_area->response_block;
2565                 QDIO_DBF_HEX2(1,setup,&ptr,QDIO_DBF_SETUP_LEN);
2566                 result=-EIO;
2567                 goto out;
2568         }
2569
2570         QDIO_DBF_TEXT2(0,setup,"setscind");
2571         QDIO_DBF_HEX2(0,setup,&real_addr_local_summary_bit,
2572                       sizeof(unsigned long));
2573         QDIO_DBF_HEX2(0,setup,&real_addr_dev_st_chg_ind,sizeof(unsigned long));
2574         result=0;
2575 out:
2576         spin_unlock_irqrestore(&chsc_area_lock,flags);
2577         return result;
2578 }
2579
2580 /* chsc_area would have to be locked if called from outside qdio_activate */
2581 static unsigned int tiqdio_set_delay_target(qdio_irq_t *irq_ptr,
2582                                            unsigned long delay_target)
2583 {
2584         unsigned int resp_code;
2585         int result;
2586         void *ptr;
2587         unsigned long flags;
2588         char dbf_text[15];
2589
2590         if (!irq_ptr->is_thinint_irq) return -ENODEV;
2591
2592         spin_lock_irqsave(&chsc_area_lock,flags);
2593
2594         memset(chsc_area,0,sizeof(qdio_chsc_area_t));
2595         chsc_area->request_block.command_code1=0x0fe0;
2596         chsc_area->request_block.command_code2=0x1027;
2597         chsc_area->request_block.operation_data_area.set_chsc_fast.
2598                 delay_target=delay_target<<16;
2599
2600         result=qdio_chsc(chsc_area);
2601         if (result) {
2602                 QDIO_PRINT_WARN("could not set delay target on irq x%x, " \
2603                                 "cc=%i. Continuing.\n",irq_ptr->irq,result);
2604                 result=-EIO;
2605                 goto out;
2606         }
2607
2608         resp_code=chsc_area->response_block.response_code;
2609         if (resp_code!=QDIO_CHSC_RESPONSE_CODE_OK) {
2610                 QDIO_PRINT_WARN("response upon setting delay target " \
2611                                 "is 0x%x. Continuing.\n",resp_code);
2612                 sprintf(dbf_text,"sdtR%4x",resp_code);
2613                 QDIO_DBF_TEXT1(0,trace,dbf_text);
2614                 QDIO_DBF_TEXT1(0,setup,dbf_text);
2615                 ptr=&chsc_area->response_block;
2616                 QDIO_DBF_HEX2(1,trace,&ptr,QDIO_DBF_TRACE_LEN);
2617         }
2618         QDIO_DBF_TEXT2(0,trace,"delytrgt");
2619         QDIO_DBF_HEX2(0,trace,&delay_target,sizeof(unsigned long));
2620         result=0;
2621 out:
2622         spin_unlock_irqrestore(&chsc_area_lock,flags);
2623         return result;
2624 }
2625
2626 int qdio_cleanup(int irq,int how)
2627 {
2628         qdio_irq_t *irq_ptr;
2629         int i,result;
2630         int do_an_irqrestore=0;
2631         unsigned long flags;
2632         int timeout;
2633         char dbf_text[15];
2634
2635         result=0;
2636         sprintf(dbf_text,"qcln%4x",irq);
2637         QDIO_DBF_TEXT1(0,trace,dbf_text);
2638         QDIO_DBF_TEXT0(0,setup,dbf_text);
2639
2640         irq_ptr=qdio_get_irq_ptr(irq);
2641         if (!irq_ptr) return -ENODEV;
2642
2643         down(&irq_ptr->setting_up_lock);
2644
2645         /* mark all qs as uninteresting */
2646         for (i=0;i<irq_ptr->no_input_qs;i++) {
2647                 atomic_set(&irq_ptr->input_qs[i]->is_in_shutdown,1);
2648         }
2649         for (i=0;i<irq_ptr->no_output_qs;i++) {
2650                 atomic_set(&irq_ptr->output_qs[i]->is_in_shutdown,1);
2651         }
2652
2653         tasklet_kill(&tiqdio_tasklet);
2654
2655         for (i=0;i<irq_ptr->no_input_qs;i++) {
2656                 qdio_unmark_q(irq_ptr->input_qs[i]);
2657                 tasklet_kill(&irq_ptr->input_qs[i]->tasklet);
2658                 if (qdio_wait_for_no_use_count(&irq_ptr->input_qs[i]->
2659                                                use_count))
2660                         result=-EINPROGRESS;
2661         }
2662
2663         for (i=0;i<irq_ptr->no_output_qs;i++) {
2664                 tasklet_kill(&irq_ptr->output_qs[i]->tasklet);
2665                 if (qdio_wait_for_no_use_count(&irq_ptr->output_qs[i]->
2666                                                use_count))
2667                         result=-EINPROGRESS;
2668         }
2669
2670         atomic_set(&irq_ptr->interrupt_has_been_cleaned,0);
2671
2672         /* cleanup subchannel */
2673         s390irq_spin_lock_irqsave(irq,flags);
2674         if (how&QDIO_FLAG_CLEANUP_USING_CLEAR) {
2675                 clear_IO(irq_ptr->irq,QDIO_DOING_CLEANUP,0);
2676                 timeout=QDIO_CLEANUP_CLEAR_TIMEOUT;
2677         } else if (how&QDIO_FLAG_CLEANUP_USING_HALT) {
2678                 halt_IO(irq_ptr->irq,QDIO_DOING_CLEANUP,0);
2679                 timeout=QDIO_CLEANUP_HALT_TIMEOUT;
2680         } else { /* default behaviour */
2681                 halt_IO(irq_ptr->irq,QDIO_DOING_CLEANUP,0);
2682                 timeout=QDIO_CLEANUP_HALT_TIMEOUT;
2683         }
2684         s390irq_spin_unlock_irqrestore(irq,flags);
2685
2686         if (qdio_sleepon(&irq_ptr->interrupt_has_been_cleaned,
2687                          timeout,irq_ptr)==-ETIME) {
2688                 s390irq_spin_lock_irqsave(irq,flags);
2689                 QDIO_PRINT_INFO("Did not get interrupt on %s_IO, " \
2690                                 "irq=0x%x.\n",
2691                                 (how==QDIO_FLAG_CLEANUP_USING_CLEAR)?
2692                                 "clear":"halt",irq);
2693                 do_an_irqrestore=1;
2694         }
2695
2696         if (irq_ptr->is_thinint_irq) {
2697                 qdio_put_indicator((__u32*)irq_ptr->dev_st_chg_ind);
2698                 tiqdio_set_subchannel_ind(irq_ptr,1); /* reset adapter
2699                                                         interrupt indicators */
2700         }
2701
2702         /* exchange int handlers, if necessary */
2703         if ((void*)ioinfo[irq]->irq_desc.handler
2704             ==(void*)qdio_handler) {
2705                 ioinfo[irq]->irq_desc.handler=
2706                         irq_ptr->original_int_handler;
2707 /*              irq_ptr->original_int_handler=NULL; */
2708         }
2709
2710         qdio_set_state(irq_ptr,QDIO_IRQ_STATE_INACTIVE);
2711
2712         if (do_an_irqrestore)
2713                 s390irq_spin_unlock_irqrestore(irq,flags);
2714
2715         up(&irq_ptr->setting_up_lock);
2716
2717         qdio_remove_irq_ptr(irq_ptr);
2718         qdio_release_irq_memory(irq_ptr);
2719
2720         QDIO_DBF_TEXT3(0,setup,"MOD_DEC_");
2721         MOD_DEC_USE_COUNT;
2722
2723         return result;
2724 }
2725
2726 unsigned long qdio_get_characteristics(int irq)
2727 {
2728         qdio_irq_t *irq_ptr;
2729         int result=0;
2730
2731         irq_ptr=qdio_get_irq_ptr(irq);
2732         if (!irq_ptr) return -ENODEV;
2733
2734         if (irq_ptr->state!=QDIO_IRQ_STATE_ACTIVE) {
2735                 return -EBUSY;
2736         }
2737
2738         if (irq_ptr->state==QDIO_IRQ_STATE_INACTIVE) {
2739                 result|=QDIO_STATE_INACTIVE;
2740         } else if (irq_ptr->state==QDIO_IRQ_STATE_ESTABLISHED) {
2741                 result|=QDIO_STATE_ESTABLISHED;
2742         } else if (irq_ptr->state==QDIO_IRQ_STATE_ACTIVE) {
2743                 result|=QDIO_STATE_ACTIVE;
2744         } else if (irq_ptr->state==QDIO_IRQ_STATE_STOPPED) {
2745                 result|=QDIO_STATE_STOPPED;
2746         }
2747
2748         if (irq_ptr->hydra_gives_outbound_pcis)
2749                 result|=QDIO_STATE_MUST_USE_OUTB_PCI;
2750
2751         return result;
2752 }
2753
2754 int qdio_initialize(qdio_initialize_t *init_data)
2755 {
2756         int i,ciw_cnt;
2757         unsigned long saveflags;
2758         qdio_irq_t *irq_ptr=NULL;
2759         int result,result2;
2760         int found;
2761         unsigned long flags;
2762         char dbf_text[20]; /* if a printf printed out more than 8 chars */
2763
2764         down(&init_sema);
2765
2766         sprintf(dbf_text,"qini%4x",init_data->irq);
2767         QDIO_DBF_TEXT0(0,setup,dbf_text);
2768         QDIO_DBF_TEXT0(0,trace,dbf_text);
2769         sprintf(dbf_text,"qfmt:%x",init_data->q_format);
2770         QDIO_DBF_TEXT0(0,setup,dbf_text);
2771         QDIO_DBF_HEX0(0,setup,init_data->adapter_name,8);
2772         sprintf(dbf_text,"qpff%4x",init_data->qib_param_field_format);
2773         QDIO_DBF_TEXT0(0,setup,dbf_text);
2774         QDIO_DBF_HEX0(0,setup,&init_data->qib_param_field,sizeof(char*));
2775         QDIO_DBF_HEX0(0,setup,&init_data->input_slib_elements,sizeof(long*));
2776         QDIO_DBF_HEX0(0,setup,&init_data->output_slib_elements,sizeof(long*));
2777         sprintf(dbf_text,"miit%4x",init_data->min_input_threshold);
2778         QDIO_DBF_TEXT0(0,setup,dbf_text);
2779         sprintf(dbf_text,"mait%4x",init_data->min_input_threshold);
2780         QDIO_DBF_TEXT0(0,setup,dbf_text);
2781         sprintf(dbf_text,"miot%4x",init_data->max_output_threshold);
2782         QDIO_DBF_TEXT0(0,setup,dbf_text);
2783         sprintf(dbf_text,"maot%4x",init_data->max_output_threshold);
2784         QDIO_DBF_TEXT0(0,setup,dbf_text);
2785         sprintf(dbf_text,"niq:%4x",init_data->no_input_qs);
2786         QDIO_DBF_TEXT0(0,setup,dbf_text);
2787         sprintf(dbf_text,"noq:%4x",init_data->no_output_qs);
2788         QDIO_DBF_TEXT0(0,setup,dbf_text);
2789         QDIO_DBF_HEX0(0,setup,&init_data->input_handler,sizeof(void*));
2790         QDIO_DBF_HEX0(0,setup,&init_data->output_handler,sizeof(void*));
2791         QDIO_DBF_HEX0(0,setup,&init_data->int_parm,sizeof(long));
2792         QDIO_DBF_HEX0(0,setup,&init_data->flags,sizeof(long));
2793         QDIO_DBF_HEX0(0,setup,&init_data->input_sbal_addr_array,sizeof(void*));
2794         QDIO_DBF_HEX0(0,setup,&init_data->output_sbal_addr_array,sizeof(void*));
2795         flags=init_data->flags;
2796
2797         /* sanity checks */
2798         if (qdio_get_irq_ptr(init_data->irq)) {
2799                 result=-EBUSY;
2800                 goto out;
2801         }
2802
2803         if (ioinfo[init_data->irq]==INVALID_STORAGE_AREA) {
2804                 result=-ENODEV;
2805                 goto out;
2806         }
2807
2808         if (!ioinfo[init_data->irq]) {
2809                 QDIO_PRINT_WARN("ioinfo[%i] is NULL!\n",init_data->irq);
2810                 result=-ENODEV;
2811                 goto out;
2812         }
2813
2814 #define DEVSTAT_FLAG_IRQ_QDIO ~0UL
2815         if (!(ioinfo[init_data->irq]->devstat.flag&DEVSTAT_FLAG_IRQ_QDIO)) {
2816                 QDIO_PRINT_WARN("ioinfo[%i]->devstat.flag=0x%08x\n",
2817                                 init_data->irq,
2818                                 ioinfo[init_data->irq]->devstat.flag);
2819                 result=-ENODEV;
2820                 goto out;
2821         }
2822
2823         if ( (init_data->no_input_qs>QDIO_MAX_QUEUES_PER_IRQ) ||
2824              (init_data->no_output_qs>QDIO_MAX_QUEUES_PER_IRQ) ||
2825              ((init_data->no_input_qs) && (!init_data->input_handler)) ||
2826              ((init_data->no_output_qs) && (!init_data->output_handler)) ) {
2827                 result=-EINVAL;
2828                 goto out;
2829         }
2830
2831         if ( (init_data->flags&QDIO_INBOUND_0COPY_SBALS)&&
2832              (!init_data->input_sbal_addr_array) ) {
2833                 result=-EINVAL;
2834                 goto out;
2835         }
2836         if ( (init_data->flags&QDIO_OUTBOUND_0COPY_SBALS)&&
2837              (!init_data->output_sbal_addr_array) ) {
2838                 result=-EINVAL;
2839                 goto out;
2840         }
2841
2842         /* create irq */
2843         irq_ptr=kmalloc(sizeof(qdio_irq_t),GFP_DMA);
2844
2845         QDIO_DBF_TEXT0(0,setup,"irq_ptr:");
2846         QDIO_DBF_HEX0(0,setup,&irq_ptr,sizeof(void*));
2847
2848         if (!irq_ptr) {
2849                 QDIO_PRINT_ERR("kmalloc of irq_ptr failed!\n");
2850                 result=-ENOMEM;
2851                 goto out;
2852         }
2853
2854         memset(irq_ptr,0,sizeof(qdio_irq_t)); /* wipes qib.ac,
2855                                                  required by ar7063 */
2856
2857         irq_ptr->qdr=kmalloc(sizeof(qdr_t),GFP_DMA);
2858         if (!(irq_ptr->qdr)) {
2859                 kfree(irq_ptr);
2860                 QDIO_PRINT_ERR("kmalloc of irq_ptr->qdr failed!\n");
2861                 result=-ENOMEM;
2862                 goto out;
2863         }
2864         memset(irq_ptr->qdr,0,sizeof(qdr_t));
2865         QDIO_DBF_TEXT0(0,setup,"qdr:");
2866         QDIO_DBF_HEX0(0,setup,&irq_ptr->qdr,sizeof(void*));
2867
2868         init_waitqueue_head(&irq_ptr->wait_q);
2869
2870         irq_ptr->int_parm=init_data->int_parm;
2871
2872         irq_ptr->irq=init_data->irq;
2873         irq_ptr->no_input_qs=init_data->no_input_qs;
2874         irq_ptr->no_output_qs=init_data->no_output_qs;
2875
2876         if (init_data->q_format==QDIO_IQDIO_QFMT) {
2877                 irq_ptr->is_iqdio_irq=1;
2878                 irq_ptr->is_thinint_irq=1;
2879         } else {
2880                 irq_ptr->is_iqdio_irq=0;
2881                 irq_ptr->is_thinint_irq=hydra_thinints;
2882         }
2883         sprintf(dbf_text,"is_i_t%1x%1x",
2884                 irq_ptr->is_iqdio_irq,irq_ptr->is_thinint_irq);
2885         QDIO_DBF_TEXT2(0,setup,dbf_text);
2886
2887         if (irq_ptr->is_thinint_irq) {
2888                 irq_ptr->dev_st_chg_ind=qdio_get_indicator();
2889                 QDIO_DBF_HEX1(0,setup,&irq_ptr->dev_st_chg_ind,sizeof(void*));
2890                 if (!irq_ptr->dev_st_chg_ind) {
2891                         QDIO_PRINT_WARN("no indicator location available " \
2892                                         "for irq 0x%x\n",irq_ptr->irq);
2893                         qdio_release_irq_memory(irq_ptr);
2894                         result=-ENOBUFS;
2895                         goto out;
2896                 }
2897         }
2898
2899         if (flags&QDIO_PFIX)
2900                 irq_ptr->other_flags |= QDIO_PFIX;
2901
2902         /* defaults */
2903         irq_ptr->commands.eq=DEFAULT_ESTABLISH_QS_CMD;
2904         irq_ptr->commands.count_eq=DEFAULT_ESTABLISH_QS_COUNT;
2905         irq_ptr->commands.aq=DEFAULT_ACTIVATE_QS_CMD;
2906         irq_ptr->commands.count_aq=DEFAULT_ACTIVATE_QS_COUNT;
2907
2908         if (!qdio_alloc_qs(irq_ptr,init_data->no_input_qs,
2909                            init_data->no_output_qs,
2910                            init_data->input_handler,
2911                            init_data->output_handler,init_data->int_parm,
2912                            init_data->q_format,init_data->flags,
2913                            init_data->input_sbal_addr_array,
2914                            init_data->output_sbal_addr_array)) {
2915                 qdio_release_irq_memory(irq_ptr);
2916                 result=-ENOMEM;
2917                 goto out;
2918         }
2919
2920         qdio_set_state(irq_ptr,QDIO_IRQ_STATE_INACTIVE);
2921
2922         sema_init(&irq_ptr->setting_up_lock,1);
2923
2924         MOD_INC_USE_COUNT;
2925         QDIO_DBF_TEXT3(0,setup,"MOD_INC_");
2926
2927         down(&irq_ptr->setting_up_lock);
2928
2929         qdio_insert_irq_ptr(irq_ptr);
2930
2931         qdio_fill_thresholds(irq_ptr,init_data->no_input_qs,
2932                              init_data->no_output_qs,
2933                              init_data->min_input_threshold,
2934                              init_data->max_input_threshold,
2935                              init_data->min_output_threshold,
2936                              init_data->max_output_threshold);
2937
2938         /* fill in qdr */
2939         irq_ptr->qdr->qfmt=init_data->q_format;
2940         irq_ptr->qdr->iqdcnt=init_data->no_input_qs;
2941         irq_ptr->qdr->oqdcnt=init_data->no_output_qs;
2942         irq_ptr->qdr->iqdsz=sizeof(qdesfmt0_t)/4; /* size in words */
2943         irq_ptr->qdr->oqdsz=sizeof(qdesfmt0_t)/4;
2944
2945         irq_ptr->qdr->qiba=QDIO_PFIX_GET_ADDR(&irq_ptr->qib);
2946         irq_ptr->qdr->qkey=QDIO_STORAGE_ACC_KEY;
2947
2948         /* fill in qib */
2949         irq_ptr->qib.qfmt=init_data->q_format;
2950         if (init_data->no_input_qs) irq_ptr->qib.isliba=
2951                                  QDIO_PFIX_GET_ADDR(irq_ptr->input_qs[0]->slib);
2952         if (init_data->no_output_qs) irq_ptr->qib.osliba=(unsigned long)
2953                                   QDIO_PFIX_GET_ADDR(irq_ptr->output_qs[0]->slib);
2954         memcpy(irq_ptr->qib.ebcnam,init_data->adapter_name,8);
2955
2956         qdio_set_impl_params(irq_ptr,init_data->qib_param_field_format,
2957                              init_data->qib_param_field,
2958                              init_data->no_input_qs,
2959                              init_data->no_output_qs,
2960                              init_data->input_slib_elements,
2961                              init_data->output_slib_elements);
2962
2963         /* first input descriptors, then output descriptors */
2964         for (i=0;i<init_data->no_input_qs;i++) {
2965                 irq_ptr->input_qs[i]->is_iqdio_q=
2966                         (init_data->q_format==QDIO_IQDIO_QFMT)?1:0;
2967                 irq_ptr->input_qs[i]->is_thinint_q=irq_ptr->is_thinint_irq;
2968
2969                 irq_ptr->qdr->qdf0[i].sliba=
2970                         QDIO_PFIX_GET_ADDR(irq_ptr->input_qs[i]->slib);
2971
2972                 irq_ptr->qdr->qdf0[i].sla=
2973                         QDIO_PFIX_GET_ADDR(irq_ptr->input_qs[i]->sl);
2974
2975                 irq_ptr->qdr->qdf0[i].slsba=
2976                         QDIO_PFIX_GET_ADDR
2977                         ((void *)&irq_ptr->input_qs[i]->slsb.acc.val[0]);
2978
2979                 irq_ptr->qdr->qdf0[i].akey=QDIO_STORAGE_ACC_KEY;
2980                 irq_ptr->qdr->qdf0[i].bkey=QDIO_STORAGE_ACC_KEY;
2981                 irq_ptr->qdr->qdf0[i].ckey=QDIO_STORAGE_ACC_KEY;
2982                 irq_ptr->qdr->qdf0[i].dkey=QDIO_STORAGE_ACC_KEY;
2983         }
2984
2985         for (i=0;i<init_data->no_output_qs;i++) {
2986                 irq_ptr->output_qs[i]->is_iqdio_q=
2987                         (init_data->q_format==QDIO_IQDIO_QFMT)?1:0;
2988                 irq_ptr->output_qs[i]->is_thinint_q=irq_ptr->is_thinint_irq;
2989
2990                 irq_ptr->qdr->qdf0[i+init_data->no_input_qs].sliba=
2991                         QDIO_PFIX_GET_ADDR(irq_ptr->output_qs[i]->slib);
2992
2993                 irq_ptr->qdr->qdf0[i+init_data->no_input_qs].sla=
2994                         QDIO_PFIX_GET_ADDR(irq_ptr->output_qs[i]->sl);
2995
2996                 irq_ptr->qdr->qdf0[i+init_data->no_input_qs].slsba=
2997                         QDIO_PFIX_GET_ADDR
2998                         ((void *)&irq_ptr->output_qs[i]->slsb.acc.val[0]);
2999
3000                 irq_ptr->qdr->qdf0[i+init_data->no_input_qs].akey=
3001                         QDIO_STORAGE_ACC_KEY;
3002                 irq_ptr->qdr->qdf0[i+init_data->no_input_qs].bkey=
3003                         QDIO_STORAGE_ACC_KEY;
3004                 irq_ptr->qdr->qdf0[i+init_data->no_input_qs].ckey=
3005                         QDIO_STORAGE_ACC_KEY;
3006                 irq_ptr->qdr->qdf0[i+init_data->no_input_qs].dkey=
3007                         QDIO_STORAGE_ACC_KEY;
3008         }
3009         /* qdr, qib, sls, slsbs, slibs, sbales filled. */
3010
3011         s390irq_spin_lock_irqsave(irq_ptr->irq,saveflags);
3012         /* keep track of original int handler */
3013         irq_ptr->original_int_handler=ioinfo[irq_ptr->irq]->irq_desc.handler;
3014
3015         /* insert qdio int handler */
3016         ioinfo[irq_ptr->irq]->irq_desc.handler=(void*)qdio_handler;
3017
3018         s390irq_spin_unlock_irqrestore(irq_ptr->irq,saveflags);
3019
3020 #define TAKEOVER_CIW(x) irq_ptr->commands.x=ioinfo[irq_ptr->irq]->senseid.ciw[ciw_cnt].cmd; irq_ptr->commands.count_##x=ioinfo[irq_ptr->irq]->senseid.ciw[ciw_cnt].count
3021         /* get qdio commands */
3022         found=0;
3023         for (ciw_cnt=0;ciw_cnt<MAX_CIWS;ciw_cnt++) {
3024                 switch (ioinfo[irq_ptr->irq]->senseid.ciw[ciw_cnt].ct) {
3025                 case CIW_TYPE_RCD: TAKEOVER_CIW(rcd); break;
3026                 case CIW_TYPE_SII: TAKEOVER_CIW(sii); break;
3027                 case CIW_TYPE_RNI: TAKEOVER_CIW(rni); break;
3028                 case CIW_TYPE_EQUEUE: TAKEOVER_CIW(eq); found++; break;
3029                 case CIW_TYPE_AQUEUE: TAKEOVER_CIW(aq); found++; break;
3030                 }
3031                 if ( (ciw_cnt>0) &&
3032                      (ioinfo[irq_ptr->irq]->senseid.ciw[ciw_cnt].ct==0) &&
3033                      (ioinfo[irq_ptr->irq]->senseid.ciw[ciw_cnt].cmd==0) &&
3034                      (ioinfo[irq_ptr->irq]->senseid.ciw[ciw_cnt].count) )
3035                         break;
3036         }
3037         if (found<2) {
3038                 QDIO_DBF_TEXT2(1,setup,"no ciws");
3039                 QDIO_PRINT_INFO("No CIWs found for QDIO commands. Trying to " \
3040                                 "use defaults.\n");
3041         }
3042
3043         /* the thinint CHSC stuff */
3044         if (irq_ptr->is_thinint_irq) {
3045 /*              iqdio_enable_adapter_int_facility(irq_ptr);*/
3046
3047                 if (tiqdio_check_chsc_availability()) {
3048                         QDIO_PRINT_ERR("Not all CHSCs supported. " \
3049                                        "Continuing.\n");
3050                 }
3051                 result=tiqdio_set_subchannel_ind(irq_ptr,0);
3052                 if (result) {
3053                         up(&irq_ptr->setting_up_lock);
3054                         qdio_cleanup(irq_ptr->irq,
3055                                      QDIO_FLAG_CLEANUP_USING_CLEAR);
3056                         goto out;
3057                 }
3058                 tiqdio_set_delay_target(irq_ptr,TIQDIO_DELAY_TARGET);
3059         }
3060
3061         /* establish q */
3062         irq_ptr->ccw.cmd_code=irq_ptr->commands.eq;
3063         irq_ptr->ccw.flags=CCW_FLAG_SLI;
3064         irq_ptr->ccw.count=irq_ptr->commands.count_eq;
3065         irq_ptr->ccw.cda=QDIO_GET_32BIT_ADDR(QDIO_PFIX_GET_ADDR(irq_ptr->qdr));
3066
3067         s390irq_spin_lock_irqsave(irq_ptr->irq,saveflags);
3068         atomic_set(&irq_ptr->interrupt_has_arrived,0);
3069
3070         result=do_IO(irq_ptr->irq,&irq_ptr->ccw,QDIO_DOING_ESTABLISH,0,
3071                      ((irq_ptr->other_flags&QDIO_PFIX)?DOIO_USE_DIAG98:0));
3072         if (result) {
3073                 result2=do_IO(irq_ptr->irq,&irq_ptr->ccw,
3074                               QDIO_DOING_ESTABLISH,0,
3075                               ((irq_ptr->other_flags&QDIO_PFIX)?
3076                                DOIO_USE_DIAG98:0));
3077                 sprintf(dbf_text,"eq:io%4x",result);
3078                 QDIO_DBF_TEXT2(1,setup,dbf_text);
3079                 if (result2) {
3080                         sprintf(dbf_text,"eq:io%4x",result);
3081                         QDIO_DBF_TEXT2(1,setup,dbf_text);
3082                 }
3083                 QDIO_PRINT_WARN("establish queues on irq %04x: do_IO " \
3084                            "returned %i, next try returned %i\n",
3085                            irq_ptr->irq,result,result2);
3086                 result=result2;
3087         }
3088
3089         s390irq_spin_unlock_irqrestore(irq_ptr->irq,saveflags);
3090
3091         if (result) {
3092                 up(&irq_ptr->setting_up_lock);
3093                 qdio_cleanup(irq_ptr->irq,QDIO_FLAG_CLEANUP_USING_CLEAR);
3094                 goto out;
3095         }
3096
3097         result=qdio_sleepon(&irq_ptr->interrupt_has_arrived,
3098                             QDIO_ESTABLISH_TIMEOUT,irq_ptr);
3099
3100         if (result) {
3101                 QDIO_PRINT_ERR("establish queues on irq %04x: timed out\n",
3102                            irq_ptr->irq);
3103                 QDIO_DBF_TEXT2(1,setup,"eq:timeo");
3104                 up(&irq_ptr->setting_up_lock);
3105                 qdio_cleanup(irq_ptr->irq,QDIO_FLAG_CLEANUP_USING_CLEAR);
3106                 goto out;
3107         }
3108
3109         if (!(irq_ptr->io_result_dstat & DEV_STAT_DEV_END)) {
3110                 QDIO_DBF_TEXT2(1,setup,"eq:no de");
3111                 QDIO_DBF_HEX2(0,setup,&irq_ptr->io_result_dstat,
3112                               sizeof(irq_ptr->io_result_dstat));
3113                 QDIO_DBF_HEX2(0,setup,&irq_ptr->io_result_cstat,
3114                               sizeof(irq_ptr->io_result_cstat));
3115                 QDIO_DBF_HEX2(0,setup,&irq_ptr->io_result_flags,
3116                               sizeof(irq_ptr->io_result_flags));
3117                 QDIO_PRINT_ERR("establish queues on irq %04x: didn't get " \
3118                                "device end: dstat=%02x, cstat=%02x, " \
3119                                "flags=%02x\n",
3120                                irq_ptr->irq,irq_ptr->io_result_dstat,
3121                                irq_ptr->io_result_cstat,
3122                                irq_ptr->io_result_flags);
3123                 up(&irq_ptr->setting_up_lock);
3124                 qdio_cleanup(irq_ptr->irq,QDIO_FLAG_CLEANUP_USING_CLEAR);
3125                 result=-EIO;
3126                 goto out;
3127         }
3128
3129         if (irq_ptr->io_result_dstat & ~(DEV_STAT_CHN_END|DEV_STAT_DEV_END)) {
3130                 QDIO_DBF_TEXT2(1,setup,"eq:badio");
3131                 QDIO_DBF_HEX2(0,setup,&irq_ptr->io_result_dstat,
3132                               sizeof(irq_ptr->io_result_dstat));
3133                 QDIO_DBF_HEX2(0,setup,&irq_ptr->io_result_cstat,
3134                               sizeof(irq_ptr->io_result_cstat));
3135                 QDIO_DBF_HEX2(0,setup,&irq_ptr->io_result_flags,
3136                               sizeof(irq_ptr->io_result_flags));
3137                 QDIO_PRINT_ERR("establish queues on irq %04x: got " \
3138                                "the following devstat: dstat=%02x, " \
3139                                "cstat=%02x, flags=%02x\n",
3140                                irq_ptr->irq,irq_ptr->io_result_dstat,
3141                                irq_ptr->io_result_cstat,
3142                                irq_ptr->io_result_flags);
3143                 result=-EIO;
3144                 up(&irq_ptr->setting_up_lock);
3145                 goto out;
3146         }
3147
3148                 irq_ptr->qdioac=qdio_check_siga_needs(irq_ptr->irq);
3149         sprintf(dbf_text,"qdioac%2x",irq_ptr->qdioac);
3150         QDIO_DBF_TEXT2(0,setup,dbf_text);
3151
3152         /* if this gets set once, we're running under VM and can omit SVSes */
3153         if (irq_ptr->qdioac&CHSC_FLAG_SIGA_SYNC_NECESSARY) {
3154                 omit_svs=1;
3155         }
3156
3157         sprintf(dbf_text,"qib ac%2x",irq_ptr->qib.ac);
3158         QDIO_DBF_TEXT2(0,setup,dbf_text);
3159
3160         if (init_data->flags&QDIO_USE_OUTBOUND_PCIS) {
3161                 irq_ptr->hydra_gives_outbound_pcis=
3162                         irq_ptr->qib.ac&QIB_AC_OUTBOUND_PCI_SUPPORTED;
3163         } else {
3164                 irq_ptr->hydra_gives_outbound_pcis=0;
3165         }
3166         irq_ptr->sync_done_on_outb_pcis=
3167                 irq_ptr->qdioac&CHSC_FLAG_SIGA_SYNC_DONE_ON_OUTB_PCIS;
3168
3169         for (i=0;i<init_data->no_input_qs;i++) {
3170                 irq_ptr->input_qs[i]->siga_sync=
3171                         irq_ptr->qdioac&CHSC_FLAG_SIGA_SYNC_NECESSARY;
3172                 irq_ptr->input_qs[i]->siga_in=
3173                         irq_ptr->qdioac&CHSC_FLAG_SIGA_INPUT_NECESSARY;
3174                 irq_ptr->input_qs[i]->siga_out=
3175                         irq_ptr->qdioac&CHSC_FLAG_SIGA_OUTPUT_NECESSARY;
3176                 irq_ptr->input_qs[i]->siga_sync_done_on_thinints=
3177                         irq_ptr->qdioac&CHSC_FLAG_SIGA_SYNC_DONE_ON_THININTS;
3178                 irq_ptr->input_qs[i]->hydra_gives_outbound_pcis=
3179                         irq_ptr->hydra_gives_outbound_pcis;
3180                 irq_ptr->input_qs[i]->siga_sync_done_on_outb_tis=
3181                         ( (irq_ptr->qdioac&
3182                            (CHSC_FLAG_SIGA_SYNC_DONE_ON_OUTB_PCIS|
3183                             CHSC_FLAG_SIGA_SYNC_DONE_ON_THININTS))==
3184                           (CHSC_FLAG_SIGA_SYNC_DONE_ON_OUTB_PCIS|
3185                            CHSC_FLAG_SIGA_SYNC_DONE_ON_THININTS) );
3186         }
3187
3188         for (i=0;i<init_data->no_output_qs;i++) {
3189                 irq_ptr->output_qs[i]->siga_sync=
3190                         irq_ptr->qdioac&CHSC_FLAG_SIGA_SYNC_NECESSARY;
3191                 irq_ptr->output_qs[i]->siga_in=
3192                         irq_ptr->qdioac&CHSC_FLAG_SIGA_INPUT_NECESSARY;
3193                 irq_ptr->output_qs[i]->siga_out=
3194                         irq_ptr->qdioac&CHSC_FLAG_SIGA_OUTPUT_NECESSARY;
3195                 irq_ptr->output_qs[i]->siga_sync_done_on_thinints=
3196                         irq_ptr->qdioac&CHSC_FLAG_SIGA_SYNC_DONE_ON_THININTS;
3197                 irq_ptr->output_qs[i]->hydra_gives_outbound_pcis=
3198                         irq_ptr->hydra_gives_outbound_pcis;
3199                 irq_ptr->output_qs[i]->siga_sync_done_on_outb_tis=
3200                         ( (irq_ptr->qdioac&
3201                            (CHSC_FLAG_SIGA_SYNC_DONE_ON_OUTB_PCIS|
3202                             CHSC_FLAG_SIGA_SYNC_DONE_ON_THININTS))==
3203                           (CHSC_FLAG_SIGA_SYNC_DONE_ON_OUTB_PCIS|
3204                            CHSC_FLAG_SIGA_SYNC_DONE_ON_THININTS) );
3205         }
3206
3207         if (init_data->qib_param_field)
3208                 memcpy(init_data->qib_param_field,irq_ptr->qib.parm,
3209                        QDIO_MAX_BUFFERS_PER_Q);
3210
3211         qdio_set_state(irq_ptr,QDIO_IRQ_STATE_ESTABLISHED);
3212
3213         if (irq_ptr) {
3214                 up(&irq_ptr->setting_up_lock);
3215         }
3216  out:
3217         up(&init_sema);
3218
3219         return result;
3220 }
3221
3222 int qdio_activate(int irq,int flags)
3223 {
3224         qdio_irq_t *irq_ptr;
3225         int i,result=0,result2;
3226         unsigned long saveflags;
3227         char dbf_text[20]; /* see qdio_initialize */
3228
3229         irq_ptr=qdio_get_irq_ptr(irq);
3230         if (!irq_ptr) return -ENODEV;
3231
3232         down(&irq_ptr->setting_up_lock);
3233         if (irq_ptr->state==QDIO_IRQ_STATE_INACTIVE) {
3234                 result=-EBUSY;
3235                 goto out;
3236         }
3237
3238         sprintf(dbf_text,"qact%4x",irq);
3239         QDIO_DBF_TEXT2(0,setup,dbf_text);
3240         QDIO_DBF_TEXT2(0,trace,dbf_text);
3241
3242         /* activate q */
3243         irq_ptr->ccw.cmd_code=irq_ptr->commands.aq;
3244         irq_ptr->ccw.flags=CCW_FLAG_SLI;
3245         irq_ptr->ccw.count=irq_ptr->commands.count_aq;
3246         irq_ptr->ccw.cda=QDIO_GET_32BIT_ADDR(0); /* no QDIO_PFIX_GET_ADDR here,
3247                                                     not needed */
3248
3249         s390irq_spin_lock_irqsave(irq_ptr->irq,saveflags);
3250         atomic_set(&irq_ptr->interrupt_has_arrived,0);
3251
3252         result=do_IO(irq_ptr->irq,&irq_ptr->ccw,QDIO_DOING_ACTIVATE,
3253                      0,DOIO_REPORT_ALL|DOIO_DENY_PREFETCH|
3254                      ((irq_ptr->other_flags&QDIO_PFIX)?DOIO_USE_DIAG98:0));
3255         if (result) {
3256                 result2=do_IO(irq_ptr->irq,&irq_ptr->ccw,
3257                               QDIO_DOING_ACTIVATE,0,DOIO_REPORT_ALL|
3258                               ((irq_ptr->other_flags&QDIO_PFIX) ? 
3259                                DOIO_USE_DIAG98:0));
3260                 sprintf(dbf_text,"aq:io%4x",result);
3261                 QDIO_DBF_TEXT2(1,setup,dbf_text);
3262                 if (result2) {
3263                         sprintf(dbf_text,"aq:io%4x",result);
3264                         QDIO_DBF_TEXT2(1,setup,dbf_text);
3265                 }
3266                 QDIO_PRINT_WARN("activate queues on irq %04x: do_IO " \
3267                            "returned %i, next try returned %i\n",
3268                            irq_ptr->irq,result,result2);
3269                 result=result2;
3270         }
3271
3272         s390irq_spin_unlock_irqrestore(irq_ptr->irq,saveflags);
3273         if (result) {
3274                 goto out;
3275         }
3276
3277         if (!(flags&QDIO_FLAG_UNDER_INTERRUPT)) {
3278                 result=qdio_sleepon(&irq_ptr->interrupt_has_arrived,
3279                                     QDIO_ACTIVATE_TIMEOUT,irq_ptr);
3280
3281                 if (result!=-ETIME) {
3282                         QDIO_DBF_TEXT2(1,setup,"aq:badio");
3283                         QDIO_DBF_HEX2(0,setup,&irq_ptr->io_result_dstat,
3284                                       sizeof(irq_ptr->io_result_dstat));
3285                         QDIO_DBF_HEX2(0,setup,&irq_ptr->io_result_cstat,
3286                                       sizeof(irq_ptr->io_result_cstat));
3287                         QDIO_DBF_HEX2(0,setup,&irq_ptr->io_result_flags,
3288                                       sizeof(irq_ptr->io_result_flags));
3289                         QDIO_PRINT_ERR("activate queues on irq %04x: got " \
3290                                        "the following devstat: dstat=%02x, " \
3291                                        "cstat=%02x, flags=%02x\n",
3292                                        irq_ptr->irq,irq_ptr->io_result_dstat,
3293                                        irq_ptr->io_result_cstat,
3294                                        irq_ptr->io_result_flags);
3295                         result=-EIO;
3296                         goto out;
3297                 } else { /* result is -ETIME, but timeout is ok for us */
3298                         result=0;
3299                 }
3300         } else result=0;
3301
3302         for (i=0;i<irq_ptr->no_input_qs;i++) {
3303                 if (irq_ptr->is_thinint_irq) {
3304                         /* that way we know, that, if we will
3305                          * get interrupted
3306                          * by tiqdio_inbound_processing,
3307                          * qdio_unmark_q will
3308                          * not be called */
3309                         qdio_reserve_q(irq_ptr->input_qs[i]);
3310                         qdio_mark_tiq(irq_ptr->input_qs[i]);
3311                         qdio_release_q(irq_ptr->input_qs[i]);
3312                 }
3313         }
3314
3315         if (flags&QDIO_FLAG_NO_INPUT_INTERRUPT_CONTEXT) {
3316                 for (i=0;i<irq_ptr->no_input_qs;i++) {
3317                         irq_ptr->input_qs[i]->is_input_q|=
3318                                 QDIO_FLAG_NO_INPUT_INTERRUPT_CONTEXT;
3319                 }
3320         }
3321
3322         qdio_wait_nonbusy(QDIO_ACTIVATE_DELAY);
3323
3324         qdio_set_state(irq_ptr,QDIO_IRQ_STATE_ACTIVE);
3325
3326  out:
3327         up(&irq_ptr->setting_up_lock);
3328
3329         return result;
3330 }
3331
3332 /* buffers filled forwards again to make Rick happy */
3333 static inline void qdio_do_qdio_fill_input(qdio_q_t *q,unsigned int qidx,
3334                                            unsigned int count,
3335                                            qdio_buffer_t *buffers)
3336 {
3337         for (;;) {
3338                 if (!q->is_0copy_sbals_q) {
3339                         memcpy((void*)q->sbal[qidx],buffers,SBAL_SIZE);
3340                         q->qdio_buffers[qidx]=buffers;
3341                         buffers++;
3342                 }
3343                 set_slsb(&q->slsb.acc.val[qidx],SLSB_CU_INPUT_EMPTY);
3344                 count--;
3345                 if (!count) break;
3346                 qidx=(qidx+1)&(QDIO_MAX_BUFFERS_PER_Q-1);
3347         }
3348
3349         /* not necessary, as the queues are synced during the SIGA read
3350         SYNC_MEMORY;*/
3351 }
3352
3353 static inline void qdio_do_qdio_fill_output(qdio_q_t *q,unsigned int qidx,
3354                                             unsigned int count,
3355                                             qdio_buffer_t *buffers)
3356 {
3357         for (;;) {
3358                 if (!q->is_0copy_sbals_q) {
3359                         memcpy((void*)q->sbal[qidx],buffers,SBAL_SIZE);
3360                         q->qdio_buffers[qidx]=buffers;
3361                         buffers++;
3362                 }
3363                 set_slsb(&q->slsb.acc.val[qidx],SLSB_CU_OUTPUT_PRIMED);
3364                 count--;
3365                 if (!count) break;
3366                 qidx=(qidx+1)&(QDIO_MAX_BUFFERS_PER_Q-1);
3367         }
3368
3369         /* SIGA write will sync the queues
3370         SYNC_MEMORY;*/
3371 }
3372
3373 /* count must be 1 in iqdio */
3374 int do_QDIO(int irq,unsigned int callflags,unsigned int queue_number,
3375             unsigned int qidx,unsigned int count,qdio_buffer_t *buffers)
3376 {
3377         qdio_q_t *q;
3378         qdio_irq_t *irq_ptr;
3379         int result;
3380         int used_elements;
3381
3382 #ifdef QDIO_DBF_LIKE_HELL
3383         char dbf_text[20];
3384
3385         sprintf(dbf_text,"doQD%04x",irq);
3386         QDIO_DBF_TEXT3(0,trace,dbf_text);
3387 #endif /* QDIO_DBF_LIKE_HELL */
3388
3389         if ( (qidx>QDIO_MAX_BUFFERS_PER_Q) ||
3390              (count>QDIO_MAX_BUFFERS_PER_Q) ||
3391              (queue_number>QDIO_MAX_QUEUES_PER_IRQ) )
3392                 return -EINVAL;
3393
3394         if (count==0) return 0;
3395
3396         irq_ptr=qdio_get_irq_ptr(irq);
3397         if (!irq_ptr) return -ENODEV;
3398
3399 #ifdef QDIO_DBF_LIKE_HELL
3400         if (callflags&QDIO_FLAG_SYNC_INPUT)
3401                 QDIO_DBF_HEX3(0,trace,&irq_ptr->input_qs[queue_number],
3402                               sizeof(void*));
3403         else
3404                 QDIO_DBF_HEX3(0,trace,&irq_ptr->output_qs[queue_number],
3405                               sizeof(void*));
3406         sprintf(dbf_text,"flag%04x",callflags);
3407         QDIO_DBF_TEXT3(0,trace,dbf_text);
3408         sprintf(dbf_text,"qi%02xct%02x",qidx,count);
3409         QDIO_DBF_TEXT3(0,trace,dbf_text);
3410         if ( ((callflags&QDIO_FLAG_SYNC_INPUT)&&
3411               (!irq_ptr->input_qs[queue_number]->is_0copy_sbals_q)) ||
3412              ((callflags&QDIO_FLAG_SYNC_OUTPUT)&&
3413               (!irq_ptr->output_qs[queue_number]->is_0copy_sbals_q)) )
3414                 QDIO_DBF_HEX5(0,sbal,buffers,256);
3415 #endif /* QDIO_DBF_LIKE_HELL */
3416
3417         if (irq_ptr->state!=QDIO_IRQ_STATE_ACTIVE) {
3418                 return -EBUSY;
3419         }
3420
3421         if (callflags&QDIO_FLAG_SYNC_INPUT) {
3422                 /* This is the inbound handling of queues */
3423                 q=irq_ptr->input_qs[queue_number];
3424
3425                 used_elements=atomic_return_add(count,
3426                                                 &q->number_of_buffers_used);
3427
3428                 qdio_do_qdio_fill_input(q,qidx,count,buffers);
3429
3430                 if ((used_elements+count==QDIO_MAX_BUFFERS_PER_Q)&&
3431                     (callflags&QDIO_FLAG_UNDER_INTERRUPT))
3432                         atomic_swap(&q->polling,0);
3433
3434                 if (!used_elements) if (!(callflags&QDIO_FLAG_DONT_SIGA)) {
3435                         if (q->siga_in) {
3436                                 result=qdio_siga_input(q);
3437                                 if (result) {
3438                                         if (q->siga_error)
3439                                                 q->error_status_flags|=
3440                                                         QDIO_STATUS_MORE_THAN_ONE_SIGA_ERROR;
3441                                         q->error_status_flags|=
3442                                                 QDIO_STATUS_LOOK_FOR_ERROR;
3443                                         q->siga_error=result;
3444                                 }
3445                         }
3446
3447                         qdio_mark_q(q);
3448                 }
3449         } else if (callflags&QDIO_FLAG_SYNC_OUTPUT) {
3450                 /* This is the outbound handling of queues */
3451 #ifdef QDIO_PERFORMANCE_STATS
3452                 perf_stats.start_time_outbound=NOW;
3453 #endif /* QDIO_PERFORMANCE_STATS */
3454                 q=irq_ptr->output_qs[queue_number];
3455
3456                 qdio_do_qdio_fill_output(q,qidx,count,buffers);
3457
3458                 used_elements=atomic_return_add(count,
3459                                                 &q->number_of_buffers_used);
3460
3461                 if (!(callflags&QDIO_FLAG_DONT_SIGA)) {
3462                         if (q->is_iqdio_q) {
3463                                 /* one siga for every sbal */
3464                                 while (count--) {
3465                                         qdio_kick_outbound_q(q);
3466                                 }
3467
3468                                 __qdio_outbound_processing(q);
3469                         } else {
3470                                 /* under VM, we do a SIGA sync
3471                                  * unconditionally */
3472                                 SYNC_MEMORY;
3473                                 else {
3474                                         /* w/o shadow queues (else branch of
3475                                          * SYNC_MEMORY :-/ ), we try to
3476                                          * fast-requeue buffers */
3477                                         if (q->slsb.acc.val
3478                                             [(qidx+QDIO_MAX_BUFFERS_PER_Q-1)
3479                                             &(QDIO_MAX_BUFFERS_PER_Q-1)]!=
3480                                             SLSB_CU_OUTPUT_PRIMED) {
3481                                                 qdio_kick_outbound_q(q);
3482                                         } else {
3483 #ifdef QDIO_DBF_LIKE_HELL
3484                                                 QDIO_DBF_TEXT3(0,trace,
3485                                                                "fast-req");
3486 #endif /* QDIO_DBF_LIKE_HELL */
3487 #ifdef QDIO_PERFORMANCE_STATS
3488                                                 perf_stats.fast_reqs++;
3489 #endif /* QDIO_PERFORMANCE_STATS */
3490                                         }
3491                                 }
3492                                 /* only marking the q could take
3493                                  * too long, the upper layer
3494                                  * module could do a lot of
3495                                  * traffic in that time */
3496                                 __qdio_outbound_processing(q);
3497                         }
3498                 }
3499
3500 #ifdef QDIO_PERFORMANCE_STATS
3501                 perf_stats.outbound_time+=NOW-perf_stats.start_time_outbound;
3502                 perf_stats.outbound_cnt++;
3503 #endif /* QDIO_PERFORMANCE_STATS */
3504         } else {
3505                 QDIO_DBF_TEXT3(1,trace,"doQD:inv");
3506                 return -EINVAL;
3507         }
3508         return 0;
3509 }
3510
3511 #ifdef QDIO_PERFORMANCE_STATS
3512 static int qdio_perf_procfile_read(char *buffer,char **buffer_location,
3513                                    off_t offset,int buffer_length,int *eof,
3514                                    void *data)
3515 {
3516         int c=0,bucket;
3517         qdio_irq_t *irq_ptr;
3518
3519         /* we are always called with buffer_length=4k, so we all
3520            deliver on the first read */
3521         if (offset>0) return 0;
3522
3523 #define _OUTP_IT(x...) c+=sprintf(buffer+c,x)
3524         _OUTP_IT("i_p_nc/c=%lu/%lu\n",i_p_nc,i_p_c);
3525         _OUTP_IT("ii_p_nc/c=%lu/%lu\n",ii_p_nc,ii_p_c);
3526         _OUTP_IT("o_p_nc/c=%lu/%lu\n",o_p_nc,o_p_c);
3527         _OUTP_IT("Number of tasklet runs (total)                  : %u\n",
3528                  perf_stats.tl_runs);
3529         _OUTP_IT("\n");
3530         _OUTP_IT("Number of SIGA sync's issued                    : %u\n",
3531                  perf_stats.siga_syncs);
3532         _OUTP_IT("Number of SIGA in's issued                      : %u\n",
3533                  perf_stats.siga_ins);
3534         _OUTP_IT("Number of SIGA out's issued                     : %u\n",
3535                  perf_stats.siga_outs);
3536         _OUTP_IT("Number of PCIs caught                           : %u\n",
3537                  perf_stats.pcis);
3538         _OUTP_IT("Number of adapter interrupts caught             : %u\n",
3539                  perf_stats.thinints);
3540         _OUTP_IT("Number of fast requeues (outg. SBALs w/o SIGA)  : %u\n",
3541                  perf_stats.fast_reqs);
3542         _OUTP_IT("\n");
3543         _OUTP_IT("Total time of all inbound actions (us) incl. UL : %u\n",
3544                  perf_stats.inbound_time);
3545         _OUTP_IT("Number of inbound transfers                     : %u\n",
3546                  perf_stats.inbound_cnt);
3547         _OUTP_IT("Total time of all outbound do_QDIOs (us)        : %u\n",
3548                  perf_stats.outbound_time);
3549         _OUTP_IT("Number of do_QDIOs outbound                     : %u\n",
3550                  perf_stats.outbound_cnt);
3551         _OUTP_IT("\n");
3552
3553         for (bucket=0;bucket<QDIO_IRQ_BUCKETS;bucket++) {
3554                 irq_ptr=first_irq[bucket];
3555
3556                 while (irq_ptr) {
3557                         _OUTP_IT("Polling time on irq %4x" \
3558                                  "                        : %u\n",
3559                                  irq_ptr->irq,irq_ptr->input_qs[0]->
3560                                  timing.threshold);
3561                         irq_ptr=irq_ptr->next;
3562                 }
3563         }
3564
3565         return c;
3566 }
3567
3568 static struct proc_dir_entry *qdio_perf_proc_file;
3569 #endif /* QDIO_PERFORMANCE_STATS */
3570
3571 static void qdio_add_procfs_entry(void)
3572 {
3573 #ifdef QDIO_PERFORMANCE_STATS
3574         proc_perf_file_registration=0;
3575         qdio_perf_proc_file=create_proc_entry(QDIO_PERF,
3576                                               S_IFREG|0444,&proc_root);
3577         if (qdio_perf_proc_file) {
3578                 qdio_perf_proc_file->read_proc=&qdio_perf_procfile_read;
3579         } else proc_perf_file_registration=-1;
3580
3581         if (proc_perf_file_registration)
3582                 QDIO_PRINT_WARN("was not able to register perf. " \
3583                                 "proc-file (%i).\n",
3584                                 proc_perf_file_registration);
3585 #endif /* QDIO_PERFORMANCE_STATS */
3586 }
3587 #ifdef MODULE
3588 static void qdio_remove_procfs_entry(void)
3589 {
3590 #ifdef QDIO_PERFORMANCE_STATS
3591         perf_stats.tl_runs=0;
3592
3593         if (!proc_perf_file_registration) /* means if it went ok earlier */
3594                 remove_proc_entry(QDIO_PERF,&proc_root);
3595 #endif /* QDIO_PERFORMANCE_STATS */
3596 }
3597 #endif /* MODULE */
3598
3599 static void tiqdio_register_thinints(void)
3600 {
3601         char dbf_text[20];
3602         register_thinint_result=
3603                 s390_register_adapter_interrupt(&tiqdio_thinint_handler);
3604         if (register_thinint_result) {
3605                 sprintf(dbf_text,"regthn%x",(register_thinint_result&0xff));
3606                 QDIO_DBF_TEXT0(0,setup,dbf_text);
3607                 QDIO_PRINT_ERR("failed to register adapter handler " \
3608                                "(rc=%i).\nAdapter interrupts might " \
3609                                "not work. Continuing.\n",
3610                                register_thinint_result);
3611         }
3612 }
3613
3614 #ifdef MODULE
3615 static void tiqdio_unregister_thinints(void)
3616 {
3617         if (!register_thinint_result)
3618                 s390_unregister_adapter_interrupt(&tiqdio_thinint_handler);
3619 }
3620 #endif /* MODULE */
3621
3622 static int qdio_get_qdio_memory(void)
3623 {
3624         int i;
3625         indicator_used[0]=1;
3626
3627         for (i=1;i<INDICATORS_PER_CACHELINE;i++)
3628                 indicator_used[i]=0;
3629         indicators=(__u32*)kmalloc(sizeof(__u32)*(INDICATORS_PER_CACHELINE),
3630                                    GFP_KERNEL);
3631         if (!indicators) return -ENOMEM;
3632         memset(indicators,0,sizeof(__u32)*(INDICATORS_PER_CACHELINE));
3633
3634         chsc_area=(qdio_chsc_area_t *)
3635                 kmalloc(sizeof(qdio_chsc_area_t),GFP_KERNEL);
3636         QDIO_DBF_TEXT3(0,trace,"chscarea"); \
3637         QDIO_DBF_HEX3(0,trace,&chsc_area,sizeof(void*)); \
3638         if (!chsc_area) {
3639                 /* ahem... let's call it data area */
3640                 QDIO_PRINT_ERR("not enough memory for data area. Cannot " \
3641                                "initialize QDIO.\n");
3642                 kfree(indicators);
3643                 return -ENOMEM;
3644         }
3645         memset(chsc_area,0,sizeof(qdio_chsc_area_t));
3646         return 0;
3647 }
3648
3649 #ifdef MODULE
3650 static void qdio_release_qdio_memory(void)
3651 {
3652         kfree(chsc_area);
3653         if (indicators) kfree(indicators);
3654 }
3655 #endif /* MODULE */
3656
3657 int init_module(void); /* we want to use it in init_QDIO */
3658
3659 static void qdio_unregister_dbf_views(void)
3660 {
3661         if (qdio_dbf_setup)
3662                 debug_unregister(qdio_dbf_setup);
3663         if (qdio_dbf_sbal)
3664                 debug_unregister(qdio_dbf_sbal);
3665         if (qdio_dbf_sense)
3666                 debug_unregister(qdio_dbf_sense);
3667         if (qdio_dbf_trace)
3668                 debug_unregister(qdio_dbf_trace);
3669 #ifdef QDIO_DBF_LIKE_HELL
3670         if (qdio_dbf_slsb_out)
3671                 debug_unregister(qdio_dbf_slsb_out);
3672         if (qdio_dbf_slsb_in)
3673                 debug_unregister(qdio_dbf_slsb_in);
3674 #endif /* QDIO_DBF_LIKE_HELL */
3675 }
3676
3677 /* this is not __initfunc, as it is called from init_module */
3678 int init_QDIO(void)
3679 {
3680         char dbf_text[20];
3681         int res;
3682 #if defined(MODULE)||defined(QDIO_PERFORMANCE_STATS)
3683         void *ptr;
3684 #endif /* defined(MODULE)||defined(QDIO_PERFORMANCE_STATS) */
3685
3686         qdio_eyecatcher();
3687
3688         printk("qdio: loading %s\n",version);
3689
3690         res=qdio_get_qdio_memory();
3691         if (res) return res;
3692
3693         sema_init(&init_sema,1);
3694
3695         qdio_dbf_setup=debug_register(QDIO_DBF_SETUP_NAME,
3696                                       QDIO_DBF_SETUP_INDEX,
3697                                       QDIO_DBF_SETUP_NR_AREAS,
3698                                       QDIO_DBF_SETUP_LEN);
3699         if (!qdio_dbf_setup) goto oom;
3700         debug_register_view(qdio_dbf_setup,&debug_hex_ascii_view);
3701         debug_set_level(qdio_dbf_setup,QDIO_DBF_SETUP_LEVEL);
3702
3703         qdio_dbf_sbal=debug_register(QDIO_DBF_SBAL_NAME,
3704                                      QDIO_DBF_SBAL_INDEX,
3705                                      QDIO_DBF_SBAL_NR_AREAS,
3706                                      QDIO_DBF_SBAL_LEN);
3707         if (!qdio_dbf_sbal) goto oom;
3708
3709         debug_register_view(qdio_dbf_sbal,&debug_hex_ascii_view);
3710         debug_set_level(qdio_dbf_sbal,QDIO_DBF_SBAL_LEVEL);
3711
3712         qdio_dbf_sense=debug_register(QDIO_DBF_SENSE_NAME,
3713                                       QDIO_DBF_SENSE_INDEX,
3714                                       QDIO_DBF_SENSE_NR_AREAS,
3715                                       QDIO_DBF_SENSE_LEN);
3716         if (!qdio_dbf_sense) goto oom;
3717
3718         debug_register_view(qdio_dbf_sense,&debug_hex_ascii_view);
3719         debug_set_level(qdio_dbf_sense,QDIO_DBF_SENSE_LEVEL);
3720
3721         qdio_dbf_trace=debug_register(QDIO_DBF_TRACE_NAME,
3722                                       QDIO_DBF_TRACE_INDEX,
3723                                       QDIO_DBF_TRACE_NR_AREAS,
3724                                       QDIO_DBF_TRACE_LEN);
3725         if (!qdio_dbf_trace) goto oom;
3726
3727         debug_register_view(qdio_dbf_trace,&debug_hex_ascii_view);
3728         debug_set_level(qdio_dbf_trace,QDIO_DBF_TRACE_LEVEL);
3729
3730 #ifdef QDIO_DBF_LIKE_HELL
3731         qdio_dbf_slsb_out=debug_register(QDIO_DBF_SLSB_OUT_NAME,
3732                                          QDIO_DBF_SLSB_OUT_INDEX,
3733                                          QDIO_DBF_SLSB_OUT_NR_AREAS,
3734                                          QDIO_DBF_SLSB_OUT_LEN);
3735         if (!qdio_dbf_slsb_out) goto oom;
3736         debug_register_view(qdio_dbf_slsb_out,&debug_hex_ascii_view);
3737         debug_set_level(qdio_dbf_slsb_out,QDIO_DBF_SLSB_OUT_LEVEL);
3738
3739         qdio_dbf_slsb_in=debug_register(QDIO_DBF_SLSB_IN_NAME,
3740                                         QDIO_DBF_SLSB_IN_INDEX,
3741                                         QDIO_DBF_SLSB_IN_NR_AREAS,
3742                                         QDIO_DBF_SLSB_IN_LEN);
3743         if (!qdio_dbf_slsb_in) goto oom;
3744         debug_register_view(qdio_dbf_slsb_in,&debug_hex_ascii_view);
3745         debug_set_level(qdio_dbf_slsb_in,QDIO_DBF_SLSB_IN_LEVEL);
3746 #endif /* QDIO_DBF_LIKE_HELL */
3747
3748 #ifdef QDIO_PERFORMANCE_STATS
3749         memset((void*)&perf_stats,0,sizeof(perf_stats));
3750         QDIO_DBF_TEXT0(0,setup,"perfstat");
3751         ptr=&perf_stats;
3752         QDIO_DBF_HEX0(0,setup,&ptr,sizeof(void*));
3753 #endif /* QDIO_PERFORMANCE_STATS */
3754
3755 #ifdef MODULE
3756         QDIO_DBF_TEXT0(0,setup,"initmodl");
3757         ptr=&init_module;
3758         QDIO_DBF_HEX0(0,setup,&ptr,sizeof(void*));
3759 #endif /* MODULE */
3760
3761         qdio_add_procfs_entry();
3762
3763         qdio_check_for_machine_features();
3764
3765         sprintf(dbf_text,"hydrati%1x",hydra_thinints);
3766         QDIO_DBF_TEXT0(0,setup,dbf_text);
3767         sprintf(dbf_text,"omitsvs%1x",omit_svs);
3768         QDIO_DBF_TEXT0(0,setup,dbf_text);
3769
3770         tiqdio_register_thinints();
3771
3772         return 0;
3773  oom:
3774         QDIO_PRINT_ERR("not enough memory for dbf.\n");
3775         qdio_unregister_dbf_views();
3776         return -ENOMEM;
3777 }
3778
3779 #ifdef MODULE
3780 int init_module(void)
3781 {
3782         return init_QDIO();
3783 }
3784
3785 void cleanup_module(void)
3786 {
3787         tiqdio_unregister_thinints();
3788
3789         qdio_remove_procfs_entry();
3790
3791         qdio_release_qdio_memory();
3792
3793         qdio_unregister_dbf_views();
3794
3795         printk("qdio: %s: module removed\n",version);
3796 }
3797 #else /* MODULE */
3798 static int __init initcall_QDIO(void)
3799 {
3800                 return init_QDIO();
3801 }
3802 __initcall(initcall_QDIO);
3803 #endif /* MODULE */
3804
3805 EXPORT_SYMBOL(qdio_initialize);
3806 EXPORT_SYMBOL(qdio_activate);
3807 EXPORT_SYMBOL(do_QDIO);
3808 EXPORT_SYMBOL(qdio_cleanup);
3809 EXPORT_SYMBOL(qdio_eyecatcher);
3810 EXPORT_SYMBOL(qdio_synchronize);
3811