ftp://ftp.kernel.org/pub/linux/kernel/v2.6/linux-2.6.6.tar.bz2
[linux-2.6.git] / drivers / net / irda / via-ircc.h
1 /*********************************************************************
2  *                
3  * Filename:      via-ircc.h
4  * Version:       1.0
5  * Description:   Driver for the VIA VT8231/VT8233 IrDA chipsets
6  * Author:        VIA Technologies, inc
7  * Date  :        08/06/2003
8
9 Copyright (c) 1998-2003 VIA Technologies, Inc.
10
11 This program is free software; you can redistribute it and/or modify it under
12 the terms of the GNU General Public License as published by the Free Software
13 Foundation; either version 2, or (at your option) any later version.
14
15 This program is distributed in the hope that it will be useful, but WITHOUT
16 ANY WARRANTIES OR REPRESENTATIONS; without even the implied warranty of
17 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
18 See the GNU General Public License for more details.
19
20 You should have received a copy of the GNU General Public License along with
21 this program; if not, write to the Free Software Foundation, Inc.,
22 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
23
24  * Comment:
25  * jul/08/2002 : Rx buffer length should use Rx ring ptr.       
26  * Oct/28/2002 : Add SB id for 3147 and 3177.   
27  * jul/09/2002 : only implement two kind of dongle currently.
28  * Oct/02/2002 : work on VT8231 and VT8233 .
29  * Aug/06/2003 : change driver format to pci driver .
30  ********************************************************************/
31 #ifndef via_IRCC_H
32 #define via_IRCC_H
33 #include <linux/time.h>
34 #include <linux/spinlock.h>
35 #include <linux/pm.h>
36 #include <asm/io.h>
37
38 #define MAX_TX_WINDOW 7
39 #define MAX_RX_WINDOW 7
40
41 struct st_fifo_entry {
42         int status;
43         int len;
44 };
45
46 struct st_fifo {
47         struct st_fifo_entry entries[MAX_RX_WINDOW + 2];
48         int pending_bytes;
49         int head;
50         int tail;
51         int len;
52 };
53
54 struct frame_cb {
55         void *start;            /* Start of frame in DMA mem */
56         int len;                /* Lenght of frame in DMA mem */
57 };
58
59 struct tx_fifo {
60         struct frame_cb queue[MAX_TX_WINDOW + 2];       /* Info about frames in queue */
61         int ptr;                /* Currently being sent */
62         int len;                /* Lenght of queue */
63         int free;               /* Next free slot */
64         void *tail;             /* Next free start in DMA mem */
65 };
66
67
68 struct eventflag                // for keeping track of Interrupt Events
69 {
70         //--------tx part
71         unsigned char TxFIFOUnderRun;
72         unsigned char EOMessage;
73         unsigned char TxFIFOReady;
74         unsigned char EarlyEOM;
75         //--------rx part
76         unsigned char PHYErr;
77         unsigned char CRCErr;
78         unsigned char RxFIFOOverRun;
79         unsigned char EOPacket;
80         unsigned char RxAvail;
81         unsigned char TooLargePacket;
82         unsigned char SIRBad;
83         //--------unknown
84         unsigned char Unknown;
85         //----------
86         unsigned char TimeOut;
87         unsigned char RxDMATC;
88         unsigned char TxDMATC;
89 };
90
91 /* Private data for each instance */
92 struct via_ircc_cb {
93         struct st_fifo st_fifo; /* Info about received frames */
94         struct tx_fifo tx_fifo; /* Info about frames to be transmitted */
95
96         struct net_device *netdev;      /* Yes! we are some kind of netdevice */
97         struct net_device_stats stats;
98
99         struct irlap_cb *irlap; /* The link layer we are binded to */
100         struct qos_info qos;    /* QoS capabilities for this device */
101
102         chipio_t io;            /* IrDA controller information */
103         iobuff_t tx_buff;       /* Transmit buffer */
104         iobuff_t rx_buff;       /* Receive buffer */
105
106         __u8 ier;               /* Interrupt enable register */
107
108         struct timeval stamp;
109         struct timeval now;
110
111         spinlock_t lock;        /* For serializing operations */
112
113         __u32 flags;            /* Interface flags */
114         __u32 new_speed;
115         int index;              /* Instance index */
116
117         struct eventflag EventFlag;
118         struct pm_dev *dev;
119         unsigned int chip_id;   /* to remember chip id */
120         unsigned int RetryCount;
121         unsigned int RxDataReady;
122         unsigned int RxLastCount;
123 };
124
125
126 //---------I=Infrared,  H=Host, M=Misc, T=Tx, R=Rx, ST=Status,
127 //         CF=Config, CT=Control, L=Low, H=High, C=Count
128 #define  I_CF_L_0               0x10
129 #define  I_CF_H_0               0x11
130 #define  I_SIR_BOF              0x12
131 #define  I_SIR_EOF              0x13
132 #define  I_ST_CT_0              0x15
133 #define  I_ST_L_1               0x16
134 #define  I_ST_H_1               0x17
135 #define  I_CF_L_1               0x18
136 #define  I_CF_H_1               0x19
137 #define  I_CF_L_2               0x1a
138 #define  I_CF_H_2               0x1b
139 #define  I_CF_3         0x1e
140 #define  H_CT                   0x20
141 #define  H_ST                   0x21
142 #define  M_CT                   0x22
143 #define  TX_CT_1                0x23
144 #define  TX_CT_2                0x24
145 #define  TX_ST                  0x25
146 #define  RX_CT                  0x26
147 #define  RX_ST                  0x27
148 #define  RESET                  0x28
149 #define  P_ADDR         0x29
150 #define  RX_C_L         0x2a
151 #define  RX_C_H         0x2b
152 #define  RX_P_L         0x2c
153 #define  RX_P_H         0x2d
154 #define  TX_C_L         0x2e
155 #define  TX_C_H         0x2f
156 #define  TIMER          0x32
157 #define  I_CF_4                 0x33
158 #define  I_T_C_L                0x34
159 #define  I_T_C_H                0x35
160 #define  VERSION                0x3f
161 //-------------------------------
162 #define StartAddr       0x10    // the first register address
163 #define EndAddr         0x3f    // the last register address
164 #define GetBit(val,bit)  val = (unsigned char) ((val>>bit) & 0x1)
165                         // Returns the bit
166 #define SetBit(val,bit)  val= (unsigned char ) (val | (0x1 << bit))
167                         // Sets bit to 1
168 #define ResetBit(val,bit) val= (unsigned char ) (val & ~(0x1 << bit))
169                         // Sets bit to 0
170 #define PCI_CONFIG_ADDRESS 0xcf8
171 #define PCI_CONFIG_DATA    0xcfc
172
173 #define VenderID    0x1106
174 #define DeviceID1   0x8231
175 #define DeviceID2   0x3109
176 #define DeviceID3   0x3074
177 //F01_S
178 #define DeviceID4   0x3147
179 #define DeviceID5   0x3177
180 //F01_E
181
182 #define OFF   0
183 #define ON   1
184 #define DMA_TX_MODE   0x08
185 #define DMA_RX_MODE   0x04
186
187 #define DMA1   0
188 #define DMA2   0xc0
189 #define MASK1   DMA1+0x0a
190 #define MASK2   DMA2+0x14
191
192 #define Clk_bit 0x40
193 #define Tx_bit 0x01
194 #define Rd_Valid 0x08
195 #define RxBit 0x08
196
197 static void DisableDmaChannel(unsigned int channel)
198 {
199         switch (channel) {      // 8 Bit DMA channels DMAC1
200         case 0:
201                 outb(4, MASK1); //mask channel 0
202                 break;
203         case 1:
204                 outb(5, MASK1); //Mask channel 1
205                 break;
206         case 2:
207                 outb(6, MASK1); //Mask channel 2
208                 break;
209         case 3:
210                 outb(7, MASK1); //Mask channel 3
211                 break;
212         case 5:
213                 outb(5, MASK2); //Mask channel 5
214                 break;
215         case 6:
216                 outb(6, MASK2); //Mask channel 6
217                 break;
218         case 7:
219                 outb(7, MASK2); //Mask channel 7
220                 break;
221         default:
222                 break;
223         };                      //Switch
224 }
225
226 static unsigned char ReadLPCReg(int iRegNum)
227 {
228         unsigned char iVal;
229
230         outb(0x87, 0x2e);
231         outb(0x87, 0x2e);
232         outb(iRegNum, 0x2e);
233         iVal = inb(0x2f);
234         outb(0xaa, 0x2e);
235
236         return iVal;
237 }
238
239 static void WriteLPCReg(int iRegNum, unsigned char iVal)
240 {
241
242         outb(0x87, 0x2e);
243         outb(0x87, 0x2e);
244         outb(iRegNum, 0x2e);
245         outb(iVal, 0x2f);
246         outb(0xAA, 0x2e);
247 }
248
249 static __u8 ReadReg(unsigned int BaseAddr, int iRegNum)
250 {
251         return ((__u8) inb(BaseAddr + iRegNum));
252 }
253
254 static void WriteReg(unsigned int BaseAddr, int iRegNum, unsigned char iVal)
255 {
256         outb(iVal, BaseAddr + iRegNum);
257 }
258
259 static int WriteRegBit(unsigned int BaseAddr, unsigned char RegNum,
260                 unsigned char BitPos, unsigned char value)
261 {
262         __u8 Rtemp, Wtemp;
263
264         if (BitPos > 7) {
265                 return -1;
266         }
267         if ((RegNum < StartAddr) || (RegNum > EndAddr))
268                 return -1;
269         Rtemp = ReadReg(BaseAddr, RegNum);
270         if (value == 0)
271                 Wtemp = ResetBit(Rtemp, BitPos);
272         else {
273                 if (value == 1)
274                         Wtemp = SetBit(Rtemp, BitPos);
275                 else
276                         return -1;
277         }
278         WriteReg(BaseAddr, RegNum, Wtemp);
279         return 0;
280 }
281
282 static __u8 CheckRegBit(unsigned int BaseAddr, unsigned char RegNum,
283                  unsigned char BitPos)
284 {
285         __u8 temp;
286
287         if (BitPos > 7)
288                 return 0xff;
289         if ((RegNum < StartAddr) || (RegNum > EndAddr)) {
290 //     printf("what is the register %x!\n",RegNum);
291         }
292         temp = ReadReg(BaseAddr, RegNum);
293         return GetBit(temp, BitPos);
294 }
295
296 static void SetMaxRxPacketSize(__u16 iobase, __u16 size)
297 {
298         __u16 low, high;
299         if ((size & 0xe000) == 0) {
300                 low = size & 0x00ff;
301                 high = (size & 0x1f00) >> 8;
302                 WriteReg(iobase, I_CF_L_2, low);
303                 WriteReg(iobase, I_CF_H_2, high);
304
305         }
306
307 }
308
309 //for both Rx and Tx
310
311 static void SetFIFO(__u16 iobase, __u16 value)
312 {
313         switch (value) {
314         case 128:
315                 WriteRegBit(iobase, 0x11, 0, 0);
316                 WriteRegBit(iobase, 0x11, 7, 1);
317                 break;
318         case 64:
319                 WriteRegBit(iobase, 0x11, 0, 0);
320                 WriteRegBit(iobase, 0x11, 7, 0);
321                 break;
322         case 32:
323                 WriteRegBit(iobase, 0x11, 0, 1);
324                 WriteRegBit(iobase, 0x11, 7, 0);
325                 break;
326         default:
327                 WriteRegBit(iobase, 0x11, 0, 0);
328                 WriteRegBit(iobase, 0x11, 7, 0);
329         }
330
331 }
332
333 #define CRC16(BaseAddr,val)         WriteRegBit(BaseAddr,I_CF_L_0,7,val)        //0 for 32 CRC
334 /*
335 #define SetVFIR(BaseAddr,val)       WriteRegBit(BaseAddr,I_CF_H_0,5,val)
336 #define SetFIR(BaseAddr,val)        WriteRegBit(BaseAddr,I_CF_L_0,6,val)
337 #define SetMIR(BaseAddr,val)        WriteRegBit(BaseAddr,I_CF_L_0,5,val)
338 #define SetSIR(BaseAddr,val)        WriteRegBit(BaseAddr,I_CF_L_0,4,val)
339 */
340 #define SIRFilter(BaseAddr,val)     WriteRegBit(BaseAddr,I_CF_L_0,3,val)
341 #define Filter(BaseAddr,val)        WriteRegBit(BaseAddr,I_CF_L_0,2,val)
342 #define InvertTX(BaseAddr,val)      WriteRegBit(BaseAddr,I_CF_L_0,1,val)
343 #define InvertRX(BaseAddr,val)      WriteRegBit(BaseAddr,I_CF_L_0,0,val)
344 //****************************I_CF_H_0
345 #define EnableTX(BaseAddr,val)      WriteRegBit(BaseAddr,I_CF_H_0,4,val)
346 #define EnableRX(BaseAddr,val)      WriteRegBit(BaseAddr,I_CF_H_0,3,val)
347 #define EnableDMA(BaseAddr,val)     WriteRegBit(BaseAddr,I_CF_H_0,2,val)
348 #define SIRRecvAny(BaseAddr,val)    WriteRegBit(BaseAddr,I_CF_H_0,1,val)
349 #define DiableTrans(BaseAddr,val)   WriteRegBit(BaseAddr,I_CF_H_0,0,val)
350 //***************************I_SIR_BOF,I_SIR_EOF
351 #define SetSIRBOF(BaseAddr,val)     WriteReg(BaseAddr,I_SIR_BOF,val)
352 #define SetSIREOF(BaseAddr,val)     WriteReg(BaseAddr,I_SIR_EOF,val)
353 #define GetSIRBOF(BaseAddr)        ReadReg(BaseAddr,I_SIR_BOF)
354 #define GetSIREOF(BaseAddr)        ReadReg(BaseAddr,I_SIR_EOF)
355 //*******************I_ST_CT_0
356 #define EnPhys(BaseAddr,val)   WriteRegBit(BaseAddr,I_ST_CT_0,7,val)
357 #define IsModeError(BaseAddr) CheckRegBit(BaseAddr,I_ST_CT_0,6) //RO
358 #define IsVFIROn(BaseAddr)     CheckRegBit(BaseAddr,0x14,0)     //RO for VT1211 only
359 #define IsFIROn(BaseAddr)     CheckRegBit(BaseAddr,I_ST_CT_0,5) //RO
360 #define IsMIROn(BaseAddr)     CheckRegBit(BaseAddr,I_ST_CT_0,4) //RO
361 #define IsSIROn(BaseAddr)     CheckRegBit(BaseAddr,I_ST_CT_0,3) //RO
362 #define IsEnableTX(BaseAddr)  CheckRegBit(BaseAddr,I_ST_CT_0,2) //RO
363 #define IsEnableRX(BaseAddr)  CheckRegBit(BaseAddr,I_ST_CT_0,1) //RO
364 #define Is16CRC(BaseAddr)     CheckRegBit(BaseAddr,I_ST_CT_0,0) //RO
365 //***************************I_CF_3
366 #define DisableAdjacentPulseWidth(BaseAddr,val) WriteRegBit(BaseAddr,I_CF_3,5,val)      //1 disable
367 #define DisablePulseWidthAdjust(BaseAddr,val)   WriteRegBit(BaseAddr,I_CF_3,4,val)      //1 disable
368 #define UseOneRX(BaseAddr,val)                  WriteRegBit(BaseAddr,I_CF_3,1,val)      //0 use two RX
369 #define SlowIRRXLowActive(BaseAddr,val)         WriteRegBit(BaseAddr,I_CF_3,0,val)      //0 show RX high=1 in SIR
370 //***************************H_CT
371 #define EnAllInt(BaseAddr,val)   WriteRegBit(BaseAddr,H_CT,7,val)
372 #define TXStart(BaseAddr,val)    WriteRegBit(BaseAddr,H_CT,6,val)
373 #define RXStart(BaseAddr,val)    WriteRegBit(BaseAddr,H_CT,5,val)
374 #define ClearRXInt(BaseAddr,val)   WriteRegBit(BaseAddr,H_CT,4,val)     // 1 clear
375 //*****************H_ST
376 #define IsRXInt(BaseAddr)           CheckRegBit(BaseAddr,H_ST,4)
377 #define GetIntIndentify(BaseAddr)   ((ReadReg(BaseAddr,H_ST)&0xf1) >>1)
378 #define IsHostBusy(BaseAddr)        CheckRegBit(BaseAddr,H_ST,0)
379 #define GetHostStatus(BaseAddr)     ReadReg(BaseAddr,H_ST)      //RO
380 //**************************M_CT
381 #define EnTXDMA(BaseAddr,val)         WriteRegBit(BaseAddr,M_CT,7,val)
382 #define EnRXDMA(BaseAddr,val)         WriteRegBit(BaseAddr,M_CT,6,val)
383 #define SwapDMA(BaseAddr,val)         WriteRegBit(BaseAddr,M_CT,5,val)
384 #define EnInternalLoop(BaseAddr,val)  WriteRegBit(BaseAddr,M_CT,4,val)
385 #define EnExternalLoop(BaseAddr,val)  WriteRegBit(BaseAddr,M_CT,3,val)
386 //**************************TX_CT_1
387 #define EnTXFIFOHalfLevelInt(BaseAddr,val)   WriteRegBit(BaseAddr,TX_CT_1,4,val)        //half empty int (1 half)
388 #define EnTXFIFOUnderrunEOMInt(BaseAddr,val) WriteRegBit(BaseAddr,TX_CT_1,5,val)
389 #define EnTXFIFOReadyInt(BaseAddr,val)       WriteRegBit(BaseAddr,TX_CT_1,6,val)        //int when reach it threshold (setting by bit 4)
390 //**************************TX_CT_2
391 #define ForceUnderrun(BaseAddr,val)   WriteRegBit(BaseAddr,TX_CT_2,7,val)       // force an underrun int
392 #define EnTXCRC(BaseAddr,val)         WriteRegBit(BaseAddr,TX_CT_2,6,val)       //1 for FIR,MIR...0 (not SIR)
393 #define ForceBADCRC(BaseAddr,val)     WriteRegBit(BaseAddr,TX_CT_2,5,val)       //force an bad CRC
394 #define SendSIP(BaseAddr,val)         WriteRegBit(BaseAddr,TX_CT_2,4,val)       //send indication pulse for prevent SIR disturb
395 #define ClearEnTX(BaseAddr,val)       WriteRegBit(BaseAddr,TX_CT_2,3,val)       // opposite to EnTX
396 //*****************TX_ST
397 #define GetTXStatus(BaseAddr)   ReadReg(BaseAddr,TX_ST) //RO
398 //**************************RX_CT
399 #define EnRXSpecInt(BaseAddr,val)           WriteRegBit(BaseAddr,RX_CT,0,val)
400 #define EnRXFIFOReadyInt(BaseAddr,val)      WriteRegBit(BaseAddr,RX_CT,1,val)   //enable int when reach it threshold (setting by bit 7)
401 #define EnRXFIFOHalfLevelInt(BaseAddr,val)  WriteRegBit(BaseAddr,RX_CT,7,val)   //enable int when (1) half full...or (0) just not full
402 //*****************RX_ST
403 #define GetRXStatus(BaseAddr)   ReadReg(BaseAddr,RX_ST) //RO
404 //***********************P_ADDR
405 #define SetPacketAddr(BaseAddr,addr)        WriteReg(BaseAddr,P_ADDR,addr)
406 //***********************I_CF_4
407 #define EnGPIOtoRX2(BaseAddr,val)       WriteRegBit(BaseAddr,I_CF_4,7,val)
408 #define EnTimerInt(BaseAddr,val)                WriteRegBit(BaseAddr,I_CF_4,1,val)
409 #define ClearTimerInt(BaseAddr,val)     WriteRegBit(BaseAddr,I_CF_4,0,val)
410 //***********************I_T_C_L
411 #define WriteGIO(BaseAddr,val)      WriteRegBit(BaseAddr,I_T_C_L,7,val)
412 #define ReadGIO(BaseAddr)                   CheckRegBit(BaseAddr,I_T_C_L,7)
413 #define ReadRX(BaseAddr)                    CheckRegBit(BaseAddr,I_T_C_L,3)     //RO
414 #define WriteTX(BaseAddr,val)           WriteRegBit(BaseAddr,I_T_C_L,0,val)
415 //***********************I_T_C_H
416 #define EnRX2(BaseAddr,val)                 WriteRegBit(BaseAddr,I_T_C_H,7,val)
417 #define ReadRX2(BaseAddr)           CheckRegBit(BaseAddr,I_T_C_H,7)
418 //**********************Version
419 #define GetFIRVersion(BaseAddr)         ReadReg(BaseAddr,VERSION)
420
421
422 static void SetTimer(__u16 iobase, __u8 count)
423 {
424         EnTimerInt(iobase, OFF);
425         WriteReg(iobase, TIMER, count);
426         EnTimerInt(iobase, ON);
427 }
428
429
430 static void SetSendByte(__u16 iobase, __u32 count)
431 {
432         __u32 low, high;
433
434         if ((count & 0xf000) == 0) {
435                 low = count & 0x00ff;
436                 high = (count & 0x0f00) >> 8;
437                 WriteReg(iobase, TX_C_L, low);
438                 WriteReg(iobase, TX_C_H, high);
439         }
440 }
441
442 static void ResetChip(__u16 iobase, __u8 type)
443 {
444         __u8 value;
445
446         value = (type + 2) << 4;
447         WriteReg(iobase, RESET, type);
448 }
449
450 static int CkRxRecv(__u16 iobase, struct via_ircc_cb *self)
451 {
452         __u8 low, high;
453         __u16 wTmp = 0, wTmp1 = 0, wTmp_new = 0;
454
455         low = ReadReg(iobase, RX_C_L);
456         high = ReadReg(iobase, RX_C_H);
457         wTmp1 = high;
458         wTmp = (wTmp1 << 8) | low;
459         udelay(10);
460         low = ReadReg(iobase, RX_C_L);
461         high = ReadReg(iobase, RX_C_H);
462         wTmp1 = high;
463         wTmp_new = (wTmp1 << 8) | low;
464         if (wTmp_new != wTmp)
465                 return 1;
466         else
467                 return 0;
468
469 }
470
471 static __u16 RxCurCount(__u16 iobase, struct via_ircc_cb * self)
472 {
473         __u8 low, high;
474         __u16 wTmp = 0, wTmp1 = 0;
475
476         low = ReadReg(iobase, RX_P_L);
477         high = ReadReg(iobase, RX_P_H);
478         wTmp1 = high;
479         wTmp = (wTmp1 << 8) | low;
480         return wTmp;
481 }
482
483 /* This Routine can only use in recevie_complete
484  * for it will update last count.
485  */
486
487 static __u16 GetRecvByte(__u16 iobase, struct via_ircc_cb * self)
488 {
489         __u8 low, high;
490         __u16 wTmp, wTmp1, ret;
491
492         low = ReadReg(iobase, RX_P_L);
493         high = ReadReg(iobase, RX_P_H);
494         wTmp1 = high;
495         wTmp = (wTmp1 << 8) | low;
496
497
498         if (wTmp >= self->RxLastCount)
499                 ret = wTmp - self->RxLastCount;
500         else
501                 ret = (0x8000 - self->RxLastCount) + wTmp;
502         self->RxLastCount = wTmp;
503
504 /* RX_P is more actually the RX_C
505  low=ReadReg(iobase,RX_C_L);
506  high=ReadReg(iobase,RX_C_H);
507
508  if(!(high&0xe000)) {
509          temp=(high<<8)+low;
510          return temp;
511  }
512  else return 0;
513 */
514         return ret;
515 }
516
517 static void Sdelay(__u16 scale)
518 {
519         __u8 bTmp;
520         int i, j;
521
522         for (j = 0; j < scale; j++) {
523                 for (i = 0; i < 0x20; i++) {
524                         bTmp = inb(0xeb);
525                         outb(bTmp, 0xeb);
526                 }
527         }
528 }
529
530 static void Tdelay(__u16 scale)
531 {
532         __u8 bTmp;
533         int i, j;
534
535         for (j = 0; j < scale; j++) {
536                 for (i = 0; i < 0x50; i++) {
537                         bTmp = inb(0xeb);
538                         outb(bTmp, 0xeb);
539                 }
540         }
541 }
542
543
544 static void ActClk(__u16 iobase, __u8 value)
545 {
546         __u8 bTmp;
547         bTmp = ReadReg(iobase, 0x34);
548         if (value)
549                 WriteReg(iobase, 0x34, bTmp | Clk_bit);
550         else
551                 WriteReg(iobase, 0x34, bTmp & ~Clk_bit);
552 }
553
554 static void ClkTx(__u16 iobase, __u8 Clk, __u8 Tx)
555 {
556         __u8 bTmp;
557
558         bTmp = ReadReg(iobase, 0x34);
559         if (Clk == 0)
560                 bTmp &= ~Clk_bit;
561         else {
562                 if (Clk == 1)
563                         bTmp |= Clk_bit;
564         }
565         WriteReg(iobase, 0x34, bTmp);
566         Sdelay(1);
567         if (Tx == 0)
568                 bTmp &= ~Tx_bit;
569         else {
570                 if (Tx == 1)
571                         bTmp |= Tx_bit;
572         }
573         WriteReg(iobase, 0x34, bTmp);
574 }
575
576 static void Wr_Byte(__u16 iobase, __u8 data)
577 {
578         __u8 bData = data;
579 //      __u8 btmp;
580         int i;
581
582         ClkTx(iobase, 0, 1);
583
584         Tdelay(2);
585         ActClk(iobase, 1);
586         Tdelay(1);
587
588         for (i = 0; i < 8; i++) {       //LDN
589
590                 if ((bData >> i) & 0x01) {
591                         ClkTx(iobase, 0, 1);    //bit data = 1;
592                 } else {
593                         ClkTx(iobase, 0, 0);    //bit data = 1;
594                 }
595                 Tdelay(2);
596                 Sdelay(1);
597                 ActClk(iobase, 1);      //clk hi
598                 Tdelay(1);
599         }
600 }
601
602 static __u8 Rd_Indx(__u16 iobase, __u8 addr, __u8 index)
603 {
604         __u8 data = 0, bTmp, data_bit;
605         int i;
606
607         bTmp = addr | (index << 1) | 0;
608         ClkTx(iobase, 0, 0);
609         Tdelay(2);
610         ActClk(iobase, 1);
611         udelay(1);
612         Wr_Byte(iobase, bTmp);
613         Sdelay(1);
614         ClkTx(iobase, 0, 0);
615         Tdelay(2);
616         for (i = 0; i < 10; i++) {
617                 ActClk(iobase, 1);
618                 Tdelay(1);
619                 ActClk(iobase, 0);
620                 Tdelay(1);
621                 ClkTx(iobase, 0, 1);
622                 Tdelay(1);
623                 bTmp = ReadReg(iobase, 0x34);
624                 if (!(bTmp & Rd_Valid))
625                         break;
626         }
627         if (!(bTmp & Rd_Valid)) {
628                 for (i = 0; i < 8; i++) {
629                         ActClk(iobase, 1);
630                         Tdelay(1);
631                         ActClk(iobase, 0);
632                         bTmp = ReadReg(iobase, 0x34);
633                         data_bit = 1 << i;
634                         if (bTmp & RxBit)
635                                 data |= data_bit;
636                         else
637                                 data &= ~data_bit;
638                         Tdelay(2);
639                 }
640         } else {
641                 for (i = 0; i < 2; i++) {
642                         ActClk(iobase, 1);
643                         Tdelay(1);
644                         ActClk(iobase, 0);
645                         Tdelay(2);
646                 }
647                 bTmp = ReadReg(iobase, 0x34);
648         }
649         for (i = 0; i < 1; i++) {
650                 ActClk(iobase, 1);
651                 Tdelay(1);
652                 ActClk(iobase, 0);
653                 Tdelay(2);
654         }
655         ClkTx(iobase, 0, 0);
656         Tdelay(1);
657         for (i = 0; i < 3; i++) {
658                 ActClk(iobase, 1);
659                 Tdelay(1);
660                 ActClk(iobase, 0);
661                 Tdelay(2);
662         }
663         return data;
664 }
665
666 static void Wr_Indx(__u16 iobase, __u8 addr, __u8 index, __u8 data)
667 {
668         int i;
669         __u8 bTmp;
670
671         ClkTx(iobase, 0, 0);
672         udelay(2);
673         ActClk(iobase, 1);
674         udelay(1);
675         bTmp = addr | (index << 1) | 1;
676         Wr_Byte(iobase, bTmp);
677         Wr_Byte(iobase, data);
678         for (i = 0; i < 2; i++) {
679                 ClkTx(iobase, 0, 0);
680                 Tdelay(2);
681                 ActClk(iobase, 1);
682                 Tdelay(1);
683         }
684         ActClk(iobase, 0);
685 }
686
687 static void ResetDongle(__u16 iobase)
688 {
689         int i;
690         ClkTx(iobase, 0, 0);
691         Tdelay(1);
692         for (i = 0; i < 30; i++) {
693                 ActClk(iobase, 1);
694                 Tdelay(1);
695                 ActClk(iobase, 0);
696                 Tdelay(1);
697         }
698         ActClk(iobase, 0);
699 }
700
701 static void SetSITmode(__u16 iobase)
702 {
703
704         __u8 bTmp;
705
706         bTmp = ReadLPCReg(0x28);
707         WriteLPCReg(0x28, bTmp | 0x10); //select ITMOFF
708         bTmp = ReadReg(iobase, 0x35);
709         WriteReg(iobase, 0x35, bTmp | 0x40);    // Driver ITMOFF
710         WriteReg(iobase, 0x28, bTmp | 0x80);    // enable All interrupt
711 }
712
713 static void SI_SetMode(__u16 iobase, int mode)
714 {
715         //__u32 dTmp;
716         __u8 bTmp;
717
718         WriteLPCReg(0x28, 0x70);        // S/W Reset
719         SetSITmode(iobase);
720         ResetDongle(iobase);
721         udelay(10);
722         Wr_Indx(iobase, 0x40, 0x0, 0x17);       //RX ,APEN enable,Normal power
723         Wr_Indx(iobase, 0x40, 0x1, mode);       //Set Mode
724         Wr_Indx(iobase, 0x40, 0x2, 0xff);       //Set power to FIR VFIR > 1m
725         bTmp = Rd_Indx(iobase, 0x40, 1);
726 }
727
728 static void InitCard(__u16 iobase)
729 {
730         ResetChip(iobase, 5);
731         WriteReg(iobase, I_ST_CT_0, 0x00);      // open CHIP on
732         SetSIRBOF(iobase, 0xc0);        // hardware default value
733         SetSIREOF(iobase, 0xc1);
734 }
735
736 static void CommonInit(__u16 iobase)
737 {
738 //  EnTXCRC(iobase,0);
739         SwapDMA(iobase, OFF);
740         SetMaxRxPacketSize(iobase, 0x0fff);     //set to max:4095
741         EnRXFIFOReadyInt(iobase, OFF);
742         EnRXFIFOHalfLevelInt(iobase, OFF);
743         EnTXFIFOHalfLevelInt(iobase, OFF);
744         EnTXFIFOUnderrunEOMInt(iobase, ON);
745 //  EnTXFIFOReadyInt(iobase,ON);
746         InvertTX(iobase, OFF);
747         InvertRX(iobase, OFF);
748 //  WriteLPCReg(0xF0,0); //(if VT1211 then do this)
749         if (IsSIROn(iobase)) {
750                 SIRFilter(iobase, ON);
751                 SIRRecvAny(iobase, ON);
752         } else {
753                 SIRFilter(iobase, OFF);
754                 SIRRecvAny(iobase, OFF);
755         }
756         EnRXSpecInt(iobase, ON);
757         WriteReg(iobase, I_ST_CT_0, 0x80);
758         EnableDMA(iobase, ON);
759 }
760
761 static void SetBaudRate(__u16 iobase, __u32 rate)
762 {
763         __u8 value = 11, temp;
764
765         if (IsSIROn(iobase)) {
766                 switch (rate) {
767                 case (__u32) (2400L):
768                         value = 47;
769                         break;
770                 case (__u32) (9600L):
771                         value = 11;
772                         break;
773                 case (__u32) (19200L):
774                         value = 5;
775                         break;
776                 case (__u32) (38400L):
777                         value = 2;
778                         break;
779                 case (__u32) (57600L):
780                         value = 1;
781                         break;
782                 case (__u32) (115200L):
783                         value = 0;
784                         break;
785                 default:
786                         break;
787                 };
788         } else if (IsMIROn(iobase)) {
789                 value = 0;      // will automatically be fixed in 1.152M
790         } else if (IsFIROn(iobase)) {
791                 value = 0;      // will automatically be fixed in 4M
792         }
793         temp = (ReadReg(iobase, I_CF_H_1) & 0x03);
794         temp = temp | (value << 2);
795         WriteReg(iobase, I_CF_H_1, temp);
796 }
797
798 static void SetPulseWidth(__u16 iobase, __u8 width)
799 {
800         __u8 temp, temp1, temp2;
801
802         temp = (ReadReg(iobase, I_CF_L_1) & 0x1f);
803         temp1 = (ReadReg(iobase, I_CF_H_1) & 0xfc);
804         temp2 = (width & 0x07) << 5;
805         temp = temp | temp2;
806         temp2 = (width & 0x18) >> 3;
807         temp1 = temp1 | temp2;
808         WriteReg(iobase, I_CF_L_1, temp);
809         WriteReg(iobase, I_CF_H_1, temp1);
810 }
811
812 static void SetSendPreambleCount(__u16 iobase, __u8 count)
813 {
814         __u8 temp;
815
816         temp = ReadReg(iobase, I_CF_L_1) & 0xe0;
817         temp = temp | count;
818         WriteReg(iobase, I_CF_L_1, temp);
819
820 }
821
822 static void SetVFIR(__u16 BaseAddr, __u8 val)
823 {
824         __u8 tmp;
825
826         tmp = ReadReg(BaseAddr, I_CF_L_0);
827         WriteReg(BaseAddr, I_CF_L_0, tmp & 0x8f);
828         WriteRegBit(BaseAddr, I_CF_H_0, 5, val);
829 }
830
831 static void SetFIR(__u16 BaseAddr, __u8 val)
832 {
833         __u8 tmp;
834
835         WriteRegBit(BaseAddr, I_CF_H_0, 5, 0);
836         tmp = ReadReg(BaseAddr, I_CF_L_0);
837         WriteReg(BaseAddr, I_CF_L_0, tmp & 0x8f);
838         WriteRegBit(BaseAddr, I_CF_L_0, 6, val);
839 }
840
841 static void SetMIR(__u16 BaseAddr, __u8 val)
842 {
843         __u8 tmp;
844
845         WriteRegBit(BaseAddr, I_CF_H_0, 5, 0);
846         tmp = ReadReg(BaseAddr, I_CF_L_0);
847         WriteReg(BaseAddr, I_CF_L_0, tmp & 0x8f);
848         WriteRegBit(BaseAddr, I_CF_L_0, 5, val);
849 }
850
851 static void SetSIR(__u16 BaseAddr, __u8 val)
852 {
853         __u8 tmp;
854
855         WriteRegBit(BaseAddr, I_CF_H_0, 5, 0);
856         tmp = ReadReg(BaseAddr, I_CF_L_0);
857         WriteReg(BaseAddr, I_CF_L_0, tmp & 0x8f);
858         WriteRegBit(BaseAddr, I_CF_L_0, 4, val);
859 }
860
861 #endif                          /* via_IRCC_H */