[kernel] move lots of kernel related packages to the new system/ folder
[openwrt.git] / package / system / ltq-dsl / src / lantiq_mei.c
1 /******************************************************************************
2
3                                Copyright (c) 2009
4                             Infineon Technologies AG
5                      Am Campeon 1-12; 81726 Munich, Germany
6
7   For licensing information, see the file 'LICENSE' in the root folder of
8   this software module.
9
10 ******************************************************************************/
11
12 /*!
13   \defgroup AMAZON_S_MEI Amazon-S MEI Driver Module
14   \brief Amazon-S MEI driver module
15  */
16
17 /*!
18   \defgroup Internal Compile Parametere
19   \ingroup AMAZON_S_MEI
20   \brief exported functions for other driver use
21  */
22
23 /*!
24   \file amazon_s_mei_bsp.c
25   \ingroup AMAZON_S_MEI
26   \brief Amazon-S MEI driver file
27  */
28
29 #include <linux/kernel.h>
30 #include <linux/module.h>
31 #include <linux/version.h>
32 #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,33))
33 #include <linux/utsrelease.h>
34 #else
35 #include <generated/utsrelease.h>
36 #endif
37 #include <linux/types.h>
38 #include <linux/fs.h>
39 #include <linux/mm.h>
40 #include <linux/errno.h>
41 #include <linux/interrupt.h>
42 #include <linux/netdevice.h>
43 #include <linux/etherdevice.h>
44 #include <linux/proc_fs.h>
45 #include <linux/init.h>
46 #include <linux/ioport.h>
47 #include <linux/delay.h>
48 #include <linux/device.h>
49 #include <linux/sched.h>
50 #include <asm/uaccess.h>
51 #include <asm/hardirq.h>
52
53 #include <lantiq_soc.h>
54 #include "ifxmips_atm.h"
55 #define IFX_MEI_BSP
56 #include "ifxmips_mei_interface.h"
57
58 /*#define LTQ_RCU_RST                   IFX_RCU_RST_REQ
59 #define LTQ_RCU_RST_REQ_ARC_JTAG      IFX_RCU_RST_REQ_ARC_JTAG
60 #define LTQ_RCU_RST_REQ_DFE               IFX_RCU_RST_REQ_DFE
61 #define LTQ_RCU_RST_REQ_AFE               IFX_RCU_RST_REQ_AFE
62 #define IFXMIPS_FUSE_BASE_ADDR            IFX_FUSE_BASE_ADDR
63 #define IFXMIPS_ICU_IM0_IER               IFX_ICU_IM0_IER
64 #define IFXMIPS_ICU_IM2_IER               IFX_ICU_IM2_IER
65 #define LTQ_MEI_INT                   IFX_MEI_INT
66 #define LTQ_MEI_DYING_GASP_INT        IFX_MEI_DYING_GASP_INT
67 #define LTQ_MEI_BASE_ADDR                 IFX_MEI_SPACE_ACCESS
68 #define IFXMIPS_PMU_PWDCR                 IFX_PMU_PWDCR
69 #define IFXMIPS_MPS_CHIPID                IFX_MPS_CHIPID
70
71 #define ifxmips_port_reserve_pin          ifx_gpio_pin_reserve
72 #define ifxmips_port_set_dir_in           ifx_gpio_dir_in_set
73 #define ifxmips_port_clear_altsel0        ifx_gpio_altsel0_set
74 #define ifxmips_port_clear_altsel1        ifx_gpio_altsel1_clear
75 #define ifxmips_port_set_open_drain       ifx_gpio_open_drain_clear
76 #define ifxmips_port_free_pin             ifx_gpio_pin_free
77 #define ifxmips_mask_and_ack_irq          bsp_mask_and_ack_irq
78 #define IFXMIPS_MPS_CHIPID_VERSION_GET    IFX_MCD_CHIPID_VERSION_GET
79 #define ltq_r32(reg)                        __raw_readl(reg)
80 #define ltq_w32(val, reg)                   __raw_writel(val, reg)
81 #define ltq_w32_mask(clear, set, reg)       ltq_w32((ltq_r32(reg) & ~clear) | set, reg)
82 */
83
84 #define LTQ_RCU_RST_REQ_DFE             (1 << 7)
85 #define LTQ_RCU_RST_REQ_AFE             (1 << 11)
86
87 #define LTQ_PMU_BASE            (KSEG1 + LTQ_PMU_BASE_ADDR)
88 #define LTQ_RCU_BASE            (KSEG1 + LTQ_RCU_BASE_ADDR)
89 #define LTQ_ICU_BASE            (KSEG1 + LTQ_ICU_BASE_ADDR)
90
91 #define LTQ_PMU_PWDCR        ((u32 *)(LTQ_PMU_BASE + 0x001C))
92 #define LTQ_PMU_PWDSR        ((u32 *)(LTQ_PMU_BASE + 0x0020))
93 #define LTQ_RCU_RST          ((u32 *)(LTQ_RCU_BASE + 0x0010))
94 #define LTQ_RCU_RST_ALL      0x40000000
95
96 #define LTQ_ICU_IM0_ISR      ((u32 *)(LTQ_ICU_BASE + 0x0000))
97 #define LTQ_ICU_IM0_IER      ((u32 *)(LTQ_ICU_BASE + 0x0008))
98 #define LTQ_ICU_IM0_IOSR     ((u32 *)(LTQ_ICU_BASE + 0x0010))
99 #define LTQ_ICU_IM0_IRSR     ((u32 *)(LTQ_ICU_BASE + 0x0018))
100 #define LTQ_ICU_IM0_IMR      ((u32 *)(LTQ_ICU_BASE + 0x0020))
101
102
103 #define LTQ_ICU_IM1_ISR      ((u32 *)(LTQ_ICU_BASE + 0x0028))
104 #define LTQ_ICU_IM2_ISR      ((u32 *)(LTQ_ICU_BASE + 0x0050))
105 #define LTQ_ICU_IM3_ISR      ((u32 *)(LTQ_ICU_BASE + 0x0078))
106 #define LTQ_ICU_IM4_ISR      ((u32 *)(LTQ_ICU_BASE + 0x00A0))
107
108 #define LTQ_ICU_OFFSET       (LTQ_ICU_IM1_ISR - LTQ_ICU_IM0_ISR)
109 #define LTQ_ICU_IM2_IER         (LTQ_ICU_IM0_IER + LTQ_ICU_OFFSET)
110
111 #define IFX_MEI_EMSG(fmt, args...) pr_err("[%s %d]: " fmt,__FUNCTION__, __LINE__, ## args)
112 #define IFX_MEI_DMSG(fmt, args...) pr_debug("[%s %d]: " fmt,__FUNCTION__, __LINE__, ## args)
113
114 #define LTQ_FUSE_BASE          (KSEG1 + 0x1F107354)
115
116 #ifdef CONFIG_LTQ_MEI_FW_LOOPBACK
117 //#define DFE_MEM_TEST
118 //#define DFE_PING_TEST
119 #define DFE_ATM_LOOPBACK
120
121
122 #ifdef DFE_ATM_LOOPBACK
123 #include <asm/ifxmips/ifxmips_mei_fw_loopback.h>
124 #endif
125
126 void dfe_loopback_irq_handler (DSL_DEV_Device_t *pDev);
127
128 #endif //CONFIG_AMAZON_S_MEI_FW_LOOPBACK
129
130 DSL_DEV_Version_t bsp_mei_version = {
131         major:  5,
132         minor:  0,
133         revision:0
134 };
135 DSL_DEV_HwVersion_t bsp_chip_info;
136
137 #define IFX_MEI_DEVNAME "ifx_mei"
138 #define BSP_MAX_DEVICES 1
139
140 DSL_DEV_MeiError_t DSL_BSP_FWDownload (DSL_DEV_Device_t *, const char *, unsigned long, long *, long *);
141 DSL_DEV_MeiError_t DSL_BSP_Showtime (DSL_DEV_Device_t *, DSL_uint32_t, DSL_uint32_t);
142 DSL_DEV_MeiError_t DSL_BSP_AdslLedInit (DSL_DEV_Device_t *, DSL_DEV_LedId_t, DSL_DEV_LedType_t, DSL_DEV_LedHandler_t);
143 //DSL_DEV_MeiError_t DSL_BSP_AdslLedSet (DSL_DEV_Device_t *, DSL_DEV_LedId_t, DSL_DEV_LedMode_t);
144 DSL_DEV_MeiError_t DSL_BSP_MemoryDebugAccess (DSL_DEV_Device_t *, DSL_BSP_MemoryAccessType_t, DSL_uint32_t, DSL_uint32_t*, DSL_uint32_t);
145 DSL_DEV_MeiError_t DSL_BSP_SendCMV (DSL_DEV_Device_t *, u16 *, int, u16 *);
146
147 int DSL_BSP_KernelIoctls (DSL_DEV_Device_t *, unsigned int, unsigned long);
148
149 static DSL_DEV_MeiError_t IFX_MEI_RunAdslModem (DSL_DEV_Device_t *);
150 static DSL_DEV_MeiError_t IFX_MEI_CpuModeSet (DSL_DEV_Device_t *, DSL_DEV_CpuMode_t);
151 static DSL_DEV_MeiError_t IFX_MEI_DownloadBootCode (DSL_DEV_Device_t *);
152 static DSL_DEV_MeiError_t IFX_MEI_ArcJtagEnable (DSL_DEV_Device_t *, int);
153 static DSL_DEV_MeiError_t IFX_MEI_AdslMailboxIRQEnable (DSL_DEV_Device_t *, int);
154
155 static int IFX_MEI_GetPage (DSL_DEV_Device_t *, u32, u32, u32, u32 *, u32 *);
156 static int IFX_MEI_BarUpdate (DSL_DEV_Device_t *, int);
157
158 static ssize_t IFX_MEI_Write (DSL_DRV_file_t *, const char *, size_t, loff_t *);
159 #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,36))
160 static int IFX_MEI_UserIoctls (DSL_DRV_inode_t *, DSL_DRV_file_t *, unsigned int, unsigned long);
161 #else
162 static int IFX_MEI_UserIoctls (DSL_DRV_file_t *, unsigned int, unsigned long);
163 #endif
164 static int IFX_MEI_Open (DSL_DRV_inode_t *, DSL_DRV_file_t *);
165 static int IFX_MEI_Release (DSL_DRV_inode_t *, DSL_DRV_file_t *);
166
167 void AMAZON_SE_MEI_ARC_MUX_Test(void);
168
169 #ifdef CONFIG_PROC_FS
170 static int IFX_MEI_ProcRead (struct file *, char *, size_t, loff_t *);
171 static ssize_t IFX_MEI_ProcWrite (struct file *, const char *, size_t, loff_t *);
172
173 #define PROC_ITEMS 11
174 #define MEI_DIRNAME "ifxmips_mei"
175
176 static struct proc_dir_entry *meidir;
177 static struct file_operations IFX_MEI_ProcOperations = {
178       read:IFX_MEI_ProcRead,
179       write:IFX_MEI_ProcWrite,
180 };
181 static reg_entry_t regs[BSP_MAX_DEVICES][PROC_ITEMS];   //total items to be monitored by /proc/mei
182 #define NUM_OF_REG_ENTRY        (sizeof(regs[0])/sizeof(reg_entry_t))
183 #endif //CONFIG_PROC_FS
184
185 void IFX_MEI_ARC_MUX_Test(void);
186
187 static int adsl_dummy_ledcallback(void);
188
189 int (*ifx_mei_atm_showtime_enter)(struct port_cell_info *, void *) = NULL;
190 EXPORT_SYMBOL(ifx_mei_atm_showtime_enter);
191
192 int (*ifx_mei_atm_showtime_exit)(void) = NULL;
193 EXPORT_SYMBOL(ifx_mei_atm_showtime_exit);
194
195 static int (*g_adsl_ledcallback)(void) = adsl_dummy_ledcallback;
196
197 static unsigned int g_tx_link_rate[2] = {0};
198
199 static void *g_xdata_addr = NULL;
200
201 static u32 *mei_arc_swap_buff = NULL;   //  holding swap pages
202
203 #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,39))
204 extern void ltq_mask_and_ack_irq(unsigned int irq_nr);
205 #define MEI_MASK_AND_ACK_IRQ ltq_mask_and_ack_irq
206 #else
207 extern void ltq_mask_and_ack_irq(struct irq_data *d);
208 static void inline MEI_MASK_AND_ACK_IRQ(int x)
209 {
210         struct irq_data d;
211         d.irq = x;
212         ltq_mask_and_ack_irq(&d);
213 }
214 #endif
215 #define MEI_MAJOR       105
216 static int dev_major = MEI_MAJOR;
217
218 static struct file_operations bsp_mei_operations = {
219       owner:THIS_MODULE,
220       open:IFX_MEI_Open,
221       release:IFX_MEI_Release,
222       write:IFX_MEI_Write,
223 #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,36))
224       ioctl:IFX_MEI_UserIoctls,
225 #else
226       unlocked_ioctl:IFX_MEI_UserIoctls,
227 #endif
228 };
229
230 static DSL_DEV_Device_t dsl_devices[BSP_MAX_DEVICES];
231
232 static ifx_mei_device_private_t
233         sDanube_Mei_Private[BSP_MAX_DEVICES];
234
235 static DSL_BSP_EventCallBack_t dsl_bsp_event_callback[DSL_BSP_CB_LAST + 1];
236
237 /**
238  * Write a value to register
239  * This function writes a value to danube register
240  *
241  * \param       ul_address      The address to write
242  * \param       ul_data         The value to write
243  * \ingroup     Internal
244  */
245 static void
246 IFX_MEI_LongWordWrite (u32 ul_address, u32 ul_data)
247 {
248         IFX_MEI_WRITE_REGISTER_L (ul_data, ul_address);
249         wmb();
250         return;
251 }
252
253 /**
254  * Write a value to register
255  * This function writes a value to danube register
256  *
257  * \param       pDev            the device pointer
258  * \param       ul_address      The address to write
259  * \param       ul_data         The value to write
260  * \ingroup     Internal
261  */
262 static void
263 IFX_MEI_LongWordWriteOffset (DSL_DEV_Device_t * pDev, u32 ul_address,
264                                    u32 ul_data)
265 {
266         IFX_MEI_WRITE_REGISTER_L (ul_data, pDev->base_address + ul_address);
267         wmb();
268         return;
269 }
270
271 /**
272  * Read the danube register
273  * This function read the value from danube register
274  *
275  * \param       ul_address      The address to write
276  * \param       pul_data        Pointer to the data
277  * \ingroup     Internal
278  */
279 static void
280 IFX_MEI_LongWordRead (u32 ul_address, u32 * pul_data)
281 {
282         *pul_data = IFX_MEI_READ_REGISTER_L (ul_address);
283         rmb();
284         return;
285 }
286
287 /**
288  * Read the danube register
289  * This function read the value from danube register
290  *
291  * \param       pDev            the device pointer
292  * \param       ul_address      The address to write
293  * \param       pul_data        Pointer to the data
294  * \ingroup     Internal
295  */
296 static void
297 IFX_MEI_LongWordReadOffset (DSL_DEV_Device_t * pDev, u32 ul_address,
298                                   u32 * pul_data)
299 {
300         *pul_data = IFX_MEI_READ_REGISTER_L (pDev->base_address + ul_address);
301         rmb();
302         return;
303 }
304
305 /**
306  * Write several DWORD datas to ARC memory via ARC DMA interface
307  * This function writes several DWORD datas to ARC memory via DMA interface.
308  *
309  * \param       pDev            the device pointer
310  * \param       destaddr        The address to write
311  * \param       databuff        Pointer to the data buffer
312  * \param       databuffsize    Number of DWORDs to write
313  * \return      DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE
314  * \ingroup     Internal
315  */
316 static DSL_DEV_MeiError_t
317 IFX_MEI_DMAWrite (DSL_DEV_Device_t * pDev, u32 destaddr,
318                         u32 * databuff, u32 databuffsize)
319 {
320         u32 *p = databuff;
321         u32 temp;
322
323         if (destaddr & 3)
324                 return DSL_DEV_MEI_ERR_FAILURE;
325
326         //      Set the write transfer address
327         IFX_MEI_LongWordWriteOffset (pDev, ME_DX_AD, destaddr);
328
329         //      Write the data pushed across DMA
330         while (databuffsize--) {
331                 temp = *p;
332                 if (destaddr == MEI_TO_ARC_MAILBOX)
333                         MEI_HALF_WORD_SWAP (temp);
334                 IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_DX_DATA, temp);
335                 p++;
336         }
337
338         return DSL_DEV_MEI_ERR_SUCCESS;
339
340 }
341
342 /**
343  * Read several DWORD datas from ARC memory via ARC DMA interface
344  * This function reads several DWORD datas from ARC memory via DMA interface.
345  *
346  * \param       pDev            the device pointer
347  * \param       srcaddr         The address to read
348  * \param       databuff        Pointer to the data buffer
349  * \param       databuffsize    Number of DWORDs to read
350  * \return      DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE
351  * \ingroup     Internal
352  */
353 static DSL_DEV_MeiError_t
354 IFX_MEI_DMARead (DSL_DEV_Device_t * pDev, u32 srcaddr, u32 * databuff,
355                        u32 databuffsize)
356 {
357         u32 *p = databuff;
358         u32 temp;
359
360         if (srcaddr & 3)
361                 return DSL_DEV_MEI_ERR_FAILURE;
362
363         //      Set the read transfer address
364         IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_DX_AD, srcaddr);
365
366         //      Read the data popped across DMA
367         while (databuffsize--) {
368                 IFX_MEI_LongWordReadOffset (pDev, (u32) ME_DX_DATA, &temp);
369                 if (databuff == (u32 *) DSL_DEV_PRIVATE(pDev)->CMV_RxMsg)       // swap half word
370                         MEI_HALF_WORD_SWAP (temp);
371                 *p = temp;
372                 p++;
373         }
374
375         return DSL_DEV_MEI_ERR_SUCCESS;
376
377 }
378
379 /**
380  * Switch the ARC control mode
381  * This function switchs the ARC control mode to JTAG mode or MEI mode
382  *
383  * \param       pDev            the device pointer
384  * \param       mode            The mode want to switch: JTAG_MASTER_MODE or MEI_MASTER_MODE.
385  * \ingroup     Internal
386  */
387 static void
388 IFX_MEI_ControlModeSet (DSL_DEV_Device_t * pDev, int mode)
389 {
390         u32 temp = 0x0;
391
392         IFX_MEI_LongWordReadOffset (pDev, (u32) ME_DBG_MASTER, &temp);
393         switch (mode) {
394         case JTAG_MASTER_MODE:
395                 temp &= ~(HOST_MSTR);
396                 break;
397         case MEI_MASTER_MODE:
398                 temp |= (HOST_MSTR);
399                 break;
400         default:
401                 IFX_MEI_EMSG ("IFX_MEI_ControlModeSet: unkonwn mode [%d]\n", mode);
402                 return;
403         }
404         IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_DBG_MASTER, temp);
405 }
406
407 /**
408  * Disable ARC to MEI interrupt
409  *
410  * \param       pDev            the device pointer
411  * \ingroup     Internal
412  */
413 static void
414 IFX_MEI_IRQDisable (DSL_DEV_Device_t * pDev)
415 {
416         IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_ARC2ME_MASK,  0x0);
417 }
418
419 /**
420  * Eable ARC to MEI interrupt
421  *
422  * \param       pDev            the device pointer
423  * \ingroup     Internal
424  */
425 static void
426 IFX_MEI_IRQEnable (DSL_DEV_Device_t * pDev)
427 {
428         IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_ARC2ME_MASK, MSGAV_EN);
429 }
430
431 /**
432  * Poll for transaction complete signal
433  * This function polls and waits for transaction complete signal.
434  *
435  * \param       pDev            the device pointer
436  * \ingroup     Internal
437  */
438 static void
439 meiPollForDbgDone (DSL_DEV_Device_t * pDev)
440 {
441         u32 query = 0;
442         int i = 0;
443
444         while (i < WHILE_DELAY) {
445                 IFX_MEI_LongWordReadOffset (pDev, (u32) ME_ARC2ME_STAT,  &query);
446                 query &= (ARC_TO_MEI_DBG_DONE);
447                 if (query)
448                         break;
449                 i++;
450                 if (i == WHILE_DELAY) {
451                         IFX_MEI_EMSG ("PollforDbg fail!\n");
452                 }
453         }
454         IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_ARC2ME_STAT, ARC_TO_MEI_DBG_DONE);  // to clear this interrupt
455 }
456
457 /**
458  * ARC Debug Memory Access for a single DWORD reading.
459  * This function used for direct, address-based access to ARC memory.
460  *
461  * \param       pDev            the device pointer
462  * \param       DEC_mode        ARC memory space to used
463  * \param       address         Address to read
464  * \param       data            Pointer to data
465  * \return      DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE
466  * \ingroup     Internal
467  */
468 static DSL_DEV_MeiError_t
469 _IFX_MEI_DBGLongWordRead (DSL_DEV_Device_t * pDev, u32 DEC_mode,
470                                 u32 address, u32 * data)
471 {
472         IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_DBG_DECODE, DEC_mode);
473         IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_DBG_RD_AD, address);
474         meiPollForDbgDone (pDev);
475         IFX_MEI_LongWordReadOffset (pDev, (u32) ME_DBG_DATA, data);
476         return DSL_DEV_MEI_ERR_SUCCESS;
477 }
478
479 /**
480  * ARC Debug Memory Access for a single DWORD writing.
481  * This function used for direct, address-based access to ARC memory.
482  *
483  * \param       pDev            the device pointer
484  * \param       DEC_mode        ARC memory space to used
485  * \param       address         The address to write
486  * \param       data            The data to write
487  * \return      DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE
488  * \ingroup     Internal
489  */
490 static DSL_DEV_MeiError_t
491 _IFX_MEI_DBGLongWordWrite (DSL_DEV_Device_t * pDev, u32 DEC_mode,
492                                  u32 address, u32 data)
493 {
494         IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_DBG_DECODE, DEC_mode);
495         IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_DBG_WR_AD, address);
496         IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_DBG_DATA, data);
497         meiPollForDbgDone (pDev);
498         return DSL_DEV_MEI_ERR_SUCCESS;
499 }
500
501 /**
502  * ARC Debug Memory Access for writing.
503  * This function used for direct, address-based access to ARC memory.
504  *
505  * \param       pDev            the device pointer
506  * \param       destaddr        The address to read
507  * \param       databuffer      Pointer to data
508  * \param       databuffsize    The number of DWORDs to read
509  * \return      DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE
510  * \ingroup     Internal
511  */
512
513 static DSL_DEV_MeiError_t
514 IFX_MEI_DebugWrite (DSL_DEV_Device_t * pDev, u32 destaddr,
515                           u32 * databuff, u32 databuffsize)
516 {
517         u32 i;
518         u32 temp = 0x0;
519         u32 address = 0x0;
520         u32 *buffer = 0x0;
521
522         //      Open the debug port before DMP memory write
523         IFX_MEI_ControlModeSet (pDev, MEI_MASTER_MODE);
524
525         //      For the requested length, write the address and write the data
526         address = destaddr;
527         buffer = databuff;
528         for (i = 0; i < databuffsize; i++) {
529                 temp = *buffer;
530                 _IFX_MEI_DBGLongWordWrite (pDev, ME_DBG_DECODE_DMP1_MASK, address, temp);
531                 address += 4;
532                 buffer++;
533         }
534
535         //      Close the debug port after DMP memory write
536         IFX_MEI_ControlModeSet (pDev, JTAG_MASTER_MODE);
537
538         return DSL_DEV_MEI_ERR_SUCCESS;
539 }
540
541 /**
542  * ARC Debug Memory Access for reading.
543  * This function used for direct, address-based access to ARC memory.
544  *
545  * \param       pDev            the device pointer
546  * \param       srcaddr         The address to read
547  * \param       databuffer      Pointer to data
548  * \param       databuffsize    The number of DWORDs to read
549  * \return      DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE
550  * \ingroup     Internal
551  */
552 static DSL_DEV_MeiError_t
553 IFX_MEI_DebugRead (DSL_DEV_Device_t * pDev, u32 srcaddr, u32 * databuff, u32 databuffsize)
554 {
555         u32 i;
556         u32 temp = 0x0;
557         u32 address = 0x0;
558         u32 *buffer = 0x0;
559
560         //      Open the debug port before DMP memory read
561         IFX_MEI_ControlModeSet (pDev, MEI_MASTER_MODE);
562
563         //      For the requested length, write the address and read the data
564         address = srcaddr;
565         buffer = databuff;
566         for (i = 0; i < databuffsize; i++) {
567                 _IFX_MEI_DBGLongWordRead (pDev, ME_DBG_DECODE_DMP1_MASK, address, &temp);
568                 *buffer = temp;
569                 address += 4;
570                 buffer++;
571         }
572
573         //      Close the debug port after DMP memory read
574         IFX_MEI_ControlModeSet (pDev, JTAG_MASTER_MODE);
575
576         return DSL_DEV_MEI_ERR_SUCCESS;
577 }
578
579 /**
580  * Send a message to ARC MailBox.
581  * This function sends a message to ARC Mailbox via ARC DMA interface.
582  *
583  * \param       pDev            the device pointer
584  * \param       msgsrcbuffer    Pointer to message.
585  * \param       msgsize         The number of words to write.
586  * \return      DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE
587  * \ingroup     Internal
588  */
589 static DSL_DEV_MeiError_t
590 IFX_MEI_MailboxWrite (DSL_DEV_Device_t * pDev, u16 * msgsrcbuffer,
591                             u16 msgsize)
592 {
593         int i;
594         u32 arc_mailbox_status = 0x0;
595         u32 temp = 0;
596         DSL_DEV_MeiError_t meiMailboxError = DSL_DEV_MEI_ERR_SUCCESS;
597
598         //      Write to mailbox
599         meiMailboxError =
600                 IFX_MEI_DMAWrite (pDev, MEI_TO_ARC_MAILBOX, (u32 *) msgsrcbuffer, msgsize / 2);
601         meiMailboxError =
602                 IFX_MEI_DMAWrite (pDev, MEI_TO_ARC_MAILBOXR, (u32 *) (&temp), 1);
603
604         //      Notify arc that mailbox write completed
605         DSL_DEV_PRIVATE(pDev)->cmv_waiting = 1;
606         IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_ME2ARC_INT, MEI_TO_ARC_MSGAV);
607
608         i = 0;
609         while (i < WHILE_DELAY) {       // wait for ARC to clear the bit
610                 IFX_MEI_LongWordReadOffset (pDev, (u32) ME_ME2ARC_INT, &arc_mailbox_status);
611                 if ((arc_mailbox_status & MEI_TO_ARC_MSGAV) != MEI_TO_ARC_MSGAV)
612                         break;
613                 i++;
614                 if (i == WHILE_DELAY) {
615                         IFX_MEI_EMSG (">>> Timeout waiting for ARC to clear MEI_TO_ARC_MSGAV!!!"
616                               " MEI_TO_ARC message size = %d DWORDs <<<\n", msgsize/2);
617                         meiMailboxError = DSL_DEV_MEI_ERR_FAILURE;
618                 }
619         }
620
621         return meiMailboxError;
622 }
623
624 /**
625  * Read a message from ARC MailBox.
626  * This function reads a message from ARC Mailbox via ARC DMA interface.
627  *
628  * \param       pDev            the device pointer
629  * \param       msgsrcbuffer    Pointer to message.
630  * \param       msgsize         The number of words to read
631  * \return      DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE
632  * \ingroup     Internal
633  */
634 static DSL_DEV_MeiError_t
635 IFX_MEI_MailboxRead (DSL_DEV_Device_t * pDev, u16 * msgdestbuffer,
636                            u16 msgsize)
637 {
638         DSL_DEV_MeiError_t meiMailboxError = DSL_DEV_MEI_ERR_SUCCESS;
639         //      Read from mailbox
640         meiMailboxError =
641                 IFX_MEI_DMARead (pDev, ARC_TO_MEI_MAILBOX, (u32 *) msgdestbuffer, msgsize / 2);
642
643         //      Notify arc that mailbox read completed
644         IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_ARC2ME_STAT, ARC_TO_MEI_MSGAV);
645
646         return meiMailboxError;
647 }
648
649 /**
650  * Download boot pages to ARC.
651  * This function downloads boot pages to ARC.
652  *
653  * \param       pDev            the device pointer
654  * \return      DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE
655  * \ingroup     Internal
656  */
657 static DSL_DEV_MeiError_t
658 IFX_MEI_DownloadBootPages (DSL_DEV_Device_t * pDev)
659 {
660         int boot_loop;
661         int page_size;
662         u32 dest_addr;
663
664         /*
665          **     DMA the boot code page(s)
666          */
667
668         for (boot_loop = 1;
669              boot_loop <
670              (DSL_DEV_PRIVATE(pDev)->img_hdr-> count); boot_loop++) {
671                 if ((DSL_DEV_PRIVATE(pDev)-> img_hdr->page[boot_loop].p_size) & BOOT_FLAG) {
672                         page_size = IFX_MEI_GetPage (pDev, boot_loop,
673                                                        GET_PROG, MAXSWAPSIZE,
674                                                        mei_arc_swap_buff,
675                                                        &dest_addr);
676                         if (page_size > 0) {
677                                 IFX_MEI_DMAWrite (pDev, dest_addr,
678                                                         mei_arc_swap_buff,
679                                                         page_size);
680                         }
681                 }
682                 if ((DSL_DEV_PRIVATE(pDev)-> img_hdr->page[boot_loop].d_size) & BOOT_FLAG) {
683                         page_size = IFX_MEI_GetPage (pDev, boot_loop,
684                                                        GET_DATA, MAXSWAPSIZE,
685                                                        mei_arc_swap_buff,
686                                                        &dest_addr);
687                         if (page_size > 0) {
688                                 IFX_MEI_DMAWrite (pDev, dest_addr,
689                                                         mei_arc_swap_buff,
690                                                         page_size);
691                         }
692                 }
693         }
694         return DSL_DEV_MEI_ERR_SUCCESS;
695 }
696
697 /**
698  * Initial efuse rar.
699  **/
700 static void
701 IFX_MEI_FuseInit (DSL_DEV_Device_t * pDev)
702 {
703         u32 data = 0;
704         IFX_MEI_DMAWrite (pDev, IRAM0_BASE, &data, 1);
705         IFX_MEI_DMAWrite (pDev, IRAM0_BASE + 4, &data, 1);
706         IFX_MEI_DMAWrite (pDev, IRAM1_BASE, &data, 1);
707         IFX_MEI_DMAWrite (pDev, IRAM1_BASE + 4, &data, 1);
708         IFX_MEI_DMAWrite (pDev, BRAM_BASE, &data, 1);
709         IFX_MEI_DMAWrite (pDev, BRAM_BASE + 4, &data, 1);
710         IFX_MEI_DMAWrite (pDev, ADSL_DILV_BASE, &data, 1);
711         IFX_MEI_DMAWrite (pDev, ADSL_DILV_BASE + 4, &data, 1);
712 }
713
714 /**
715  * efuse rar program
716  **/
717 static void
718 IFX_MEI_FuseProg (DSL_DEV_Device_t * pDev)
719 {
720         u32 reg_data, fuse_value;
721         int i = 0;
722
723         IFX_MEI_LongWordRead ((u32) LTQ_RCU_RST, &reg_data);
724         while ((reg_data & 0x10000000) == 0) {
725                 IFX_MEI_LongWordRead ((u32) LTQ_RCU_RST,  &reg_data);
726                 i++;
727                 /* 0x4000 translate to  about 16 ms@111M, so should be enough */
728                 if (i == 0x4000)
729                         return;
730         }
731         // STEP a: Prepare memory for external accesses
732         // Write fuse_en bit24
733         IFX_MEI_LongWordRead ((u32) LTQ_RCU_RST, &reg_data);
734         IFX_MEI_LongWordWrite ((u32) LTQ_RCU_RST, reg_data | (1 << 24));
735
736         IFX_MEI_FuseInit (pDev);
737         for (i = 0; i < 4; i++) {
738                 IFX_MEI_LongWordRead ((u32) (LTQ_FUSE_BASE) + i * 4, &fuse_value);
739                 switch (fuse_value & 0xF0000) {
740                 case 0x80000:
741                         reg_data = ((fuse_value & RX_DILV_ADDR_BIT_MASK) |
742                                  (RX_DILV_ADDR_BIT_MASK + 0x1));
743                         IFX_MEI_DMAWrite (pDev, ADSL_DILV_BASE, &reg_data, 1);
744                         break;
745                 case 0x90000:
746                         reg_data = ((fuse_value & RX_DILV_ADDR_BIT_MASK) |
747                                  (RX_DILV_ADDR_BIT_MASK + 0x1));
748                         IFX_MEI_DMAWrite (pDev, ADSL_DILV_BASE + 4, &reg_data, 1);
749                         break;
750                 case 0xA0000:
751                         reg_data = ((fuse_value & IRAM0_ADDR_BIT_MASK) |
752                                  (IRAM0_ADDR_BIT_MASK + 0x1));
753                         IFX_MEI_DMAWrite (pDev, IRAM0_BASE, &reg_data, 1);
754                         break;
755                 case 0xB0000:
756                         reg_data = ((fuse_value & IRAM0_ADDR_BIT_MASK) |
757                                  (IRAM0_ADDR_BIT_MASK + 0x1));
758                         IFX_MEI_DMAWrite (pDev, IRAM0_BASE + 4, &reg_data, 1);
759                         break;
760                 case 0xC0000:
761                         reg_data = ((fuse_value & IRAM1_ADDR_BIT_MASK) |
762                                  (IRAM1_ADDR_BIT_MASK + 0x1));
763                         IFX_MEI_DMAWrite (pDev, IRAM1_BASE, &reg_data, 1);
764                         break;
765                 case 0xD0000:
766                         reg_data = ((fuse_value & IRAM1_ADDR_BIT_MASK) |
767                                  (IRAM1_ADDR_BIT_MASK + 0x1));
768                         IFX_MEI_DMAWrite (pDev, IRAM1_BASE + 4, &reg_data, 1);
769                         break;
770                 case 0xE0000:
771                         reg_data = ((fuse_value & BRAM_ADDR_BIT_MASK) |
772                                  (BRAM_ADDR_BIT_MASK + 0x1));
773                         IFX_MEI_DMAWrite (pDev, BRAM_BASE, &reg_data, 1);
774                         break;
775                 case 0xF0000:
776                         reg_data = ((fuse_value & BRAM_ADDR_BIT_MASK) |
777                                  (BRAM_ADDR_BIT_MASK + 0x1));
778                         IFX_MEI_DMAWrite (pDev, BRAM_BASE + 4, &reg_data, 1);
779                         break;
780                 default:        // PPE efuse
781                         break;
782                 }
783         }
784         IFX_MEI_LongWordRead ((u32) LTQ_RCU_RST, &reg_data);
785         IFX_MEI_LongWordWrite ((u32) LTQ_RCU_RST, reg_data & ~(1 << 24));
786         IFX_MEI_LongWordRead ((u32) LTQ_RCU_RST, &reg_data);
787 }
788
789 /**
790  * Enable DFE Clock
791  * This function enables DFE Clock
792  *
793  * \param       pDev            the device pointer
794  * \return      DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE
795  * \ingroup     Internal
796  */
797 static DSL_DEV_MeiError_t
798 IFX_MEI_EnableCLK (DSL_DEV_Device_t * pDev)
799 {
800         u32 arc_debug_data = 0;
801         IFX_MEI_ControlModeSet (pDev, MEI_MASTER_MODE);
802         //enable ac_clk signal
803         _IFX_MEI_DBGLongWordRead (pDev, ME_DBG_DECODE_DMP1_MASK,
804                                         CRI_CCR0, &arc_debug_data);
805         arc_debug_data |= ACL_CLK_MODE_ENABLE;
806         _IFX_MEI_DBGLongWordWrite (pDev, ME_DBG_DECODE_DMP1_MASK,
807                                          CRI_CCR0, arc_debug_data);
808         IFX_MEI_ControlModeSet (pDev, JTAG_MASTER_MODE);
809         return DSL_DEV_MEI_ERR_SUCCESS;
810 }
811
812 /**
813  * Halt the ARC.
814  * This function halts the ARC.
815  *
816  * \param       pDev            the device pointer
817  * \return      DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE
818  * \ingroup     Internal
819  */
820 static DSL_DEV_MeiError_t
821 IFX_MEI_HaltArc (DSL_DEV_Device_t * pDev)
822 {
823         u32 arc_debug_data = 0x0;
824
825         //      Switch arc control from JTAG mode to MEI mode
826         IFX_MEI_ControlModeSet (pDev, MEI_MASTER_MODE);
827         _IFX_MEI_DBGLongWordRead (pDev, MEI_DEBUG_DEC_AUX_MASK,
828                                         ARC_DEBUG, &arc_debug_data);
829         arc_debug_data |= ARC_DEBUG_HALT;
830         _IFX_MEI_DBGLongWordWrite (pDev, MEI_DEBUG_DEC_AUX_MASK,
831                                          ARC_DEBUG, arc_debug_data);
832         //      Switch arc control from MEI mode to JTAG mode
833         IFX_MEI_ControlModeSet (pDev, JTAG_MASTER_MODE);
834
835         MEI_WAIT (10);
836
837         return DSL_DEV_MEI_ERR_SUCCESS;
838 }
839
840 /**
841  * Run the ARC.
842  * This function runs the ARC.
843  *
844  * \param       pDev            the device pointer
845  * \return      DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE
846  * \ingroup     Internal
847  */
848 static DSL_DEV_MeiError_t
849 IFX_MEI_RunArc (DSL_DEV_Device_t * pDev)
850 {
851         u32 arc_debug_data = 0x0;
852
853         //      Switch arc control from JTAG mode to MEI mode- write '1' to bit0
854         IFX_MEI_ControlModeSet (pDev, MEI_MASTER_MODE);
855         _IFX_MEI_DBGLongWordRead (pDev, MEI_DEBUG_DEC_AUX_MASK,
856                                         AUX_STATUS, &arc_debug_data);
857
858         //      Write debug data reg with content ANDd with 0xFDFFFFFF (halt bit cleared)
859         arc_debug_data &= ~ARC_AUX_HALT;
860         _IFX_MEI_DBGLongWordWrite (pDev, MEI_DEBUG_DEC_AUX_MASK,
861                                          AUX_STATUS, arc_debug_data);
862
863         //      Switch arc control from MEI mode to JTAG mode- write '0' to bit0
864         IFX_MEI_ControlModeSet (pDev, JTAG_MASTER_MODE);
865         //      Enable mask for arc codeswap interrupts
866         IFX_MEI_IRQEnable (pDev);
867
868         return DSL_DEV_MEI_ERR_SUCCESS;
869
870 }
871
872 /**
873  * Reset the ARC.
874  * This function resets the ARC.
875  *
876  * \param       pDev            the device pointer
877  * \return      DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE
878  * \ingroup     Internal
879  */
880 static DSL_DEV_MeiError_t
881 IFX_MEI_ResetARC (DSL_DEV_Device_t * pDev)
882 {
883         u32 arc_debug_data = 0;
884
885         IFX_MEI_HaltArc (pDev);
886
887         IFX_MEI_LongWordRead ((u32) LTQ_RCU_RST, &arc_debug_data);
888         IFX_MEI_LongWordWrite ((u32) LTQ_RCU_RST,
889                 arc_debug_data | LTQ_RCU_RST_REQ_DFE | LTQ_RCU_RST_REQ_AFE);
890
891         // reset ARC
892         IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_RST_CTRL, MEI_SOFT_RESET);
893         IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_RST_CTRL, 0);
894
895         IFX_MEI_IRQDisable (pDev);
896
897         IFX_MEI_EnableCLK (pDev);
898
899 #if 0
900         // reset part of PPE
901         *(unsigned long *) (BSP_PPE32_SRST) = 0xC30;
902         *(unsigned long *) (BSP_PPE32_SRST) = 0xFFF;
903 #endif
904
905         DSL_DEV_PRIVATE(pDev)->modem_ready = 0;
906
907         return DSL_DEV_MEI_ERR_SUCCESS;
908 }
909
910 DSL_DEV_MeiError_t
911 DSL_BSP_Showtime (DSL_DEV_Device_t * dev, DSL_uint32_t rate_fast, DSL_uint32_t rate_intl)
912 {
913     struct port_cell_info port_cell = {0};
914
915         IFX_MEI_EMSG ("Datarate US intl = %d, fast = %d\n", (int)rate_intl,
916                             (int)rate_fast);
917
918     if ( rate_fast )
919         g_tx_link_rate[0] = rate_fast / (53 * 8);
920     if ( rate_intl )
921         g_tx_link_rate[1] = rate_intl / (53 * 8);
922
923     if ( g_tx_link_rate[0] == 0 && g_tx_link_rate[1] == 0 ) {
924         IFX_MEI_EMSG ("Got rate fail.\n");
925     }
926
927         if ( ifx_mei_atm_showtime_enter )
928         {
929             port_cell.port_num = 2;
930             port_cell.tx_link_rate[0] = g_tx_link_rate[0];
931             port_cell.tx_link_rate[1] = g_tx_link_rate[1];
932         ifx_mei_atm_showtime_enter(&port_cell, g_xdata_addr);
933         }
934         else
935         {
936                 IFX_MEI_EMSG("no hookup from ATM driver to set cell rate\n");
937         }
938
939         return DSL_DEV_MEI_ERR_SUCCESS;
940 };
941
942 /**
943  * Reset/halt/run the DFE.
944  * This function provide operations to reset/halt/run the DFE.
945  *
946  * \param       pDev            the device pointer
947  * \param       mode            which operation want to do
948  * \return      DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE
949  * \ingroup     Internal
950  */
951 static DSL_DEV_MeiError_t
952 IFX_MEI_CpuModeSet (DSL_DEV_Device_t *pDev,
953                           DSL_DEV_CpuMode_t mode)
954 {
955         DSL_DEV_MeiError_t err_ret = DSL_DEV_MEI_ERR_FAILURE;
956         switch (mode) {
957         case DSL_CPU_HALT:
958                 err_ret = IFX_MEI_HaltArc (pDev);
959                 break;
960         case DSL_CPU_RUN:
961                 err_ret = IFX_MEI_RunArc (pDev);
962                 break;
963         case DSL_CPU_RESET:
964                 err_ret = IFX_MEI_ResetARC (pDev);
965                 break;
966         default:
967                 break;
968         }
969         return err_ret;
970 }
971
972 /**
973  * Accress DFE memory.
974  * This function provide a way to access DFE memory;
975  *
976  * \param       pDev            the device pointer
977  * \param       type            read or write
978  * \param       destaddr        destination address
979  * \param       databuff        pointer to hold data
980  * \param       databuffsize    size want to read/write
981  * \return      DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE
982  * \ingroup     Internal
983  */
984 DSL_DEV_MeiError_t
985 DSL_BSP_MemoryDebugAccess (DSL_DEV_Device_t * pDev,
986                                 DSL_BSP_MemoryAccessType_t type,
987                                 DSL_uint32_t destaddr, DSL_uint32_t *databuff,
988                                 DSL_uint32_t databuffsize)
989 {
990         DSL_DEV_MeiError_t meierr = DSL_DEV_MEI_ERR_SUCCESS;
991         switch (type) {
992         case DSL_BSP_MEMORY_READ:
993                 meierr = IFX_MEI_DebugRead (pDev, (u32)destaddr, (u32*)databuff, (u32)databuffsize);
994                 break;
995         case DSL_BSP_MEMORY_WRITE:
996                 meierr = IFX_MEI_DebugWrite (pDev, (u32)destaddr, (u32*)databuff, (u32)databuffsize);
997                 break;
998         }
999         return DSL_DEV_MEI_ERR_SUCCESS;
1000 };
1001
1002 /**
1003  * Download boot code to ARC.
1004  * This function downloads boot code to ARC.
1005  *
1006  * \param       pDev            the device pointer
1007  * \return      DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE
1008  * \ingroup     Internal
1009  */
1010 static DSL_DEV_MeiError_t
1011 IFX_MEI_DownloadBootCode (DSL_DEV_Device_t *pDev)
1012 {
1013         IFX_MEI_IRQDisable (pDev);
1014
1015         IFX_MEI_EnableCLK (pDev);
1016
1017         IFX_MEI_FuseProg (pDev);        //program fuse rar
1018
1019         IFX_MEI_DownloadBootPages (pDev);
1020
1021         return DSL_DEV_MEI_ERR_SUCCESS;
1022 };
1023
1024 /**
1025  * Enable Jtag debugger interface
1026  * This function setups mips gpio to enable jtag debugger
1027  *
1028  * \param       pDev            the device pointer
1029  * \param       enable          enable or disable
1030  * \return      DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE
1031  * \ingroup     Internal
1032  */
1033 static DSL_DEV_MeiError_t
1034 IFX_MEI_ArcJtagEnable (DSL_DEV_Device_t *dev, int enable)
1035 {
1036         /*
1037         int meierr=0;
1038         u32 reg_data;
1039         switch (enable) {
1040         case 1:
1041                 //reserve gpio 9, 10, 11, 14, 19 for ARC JTAG
1042                 ifxmips_port_reserve_pin (0, 9);
1043                 ifxmips_port_reserve_pin (0, 10);
1044                 ifxmips_port_reserve_pin (0, 11);
1045                 ifxmips_port_reserve_pin (0, 14);
1046                 ifxmips_port_reserve_pin (1, 3);
1047
1048                 ifxmips_port_set_dir_in(0, 11);
1049                 ifxmips_port_clear_altsel0(0, 11);
1050                 ifxmips_port_clear_altsel1(0, 11);
1051                 ifxmips_port_set_open_drain(0, 11);
1052         //enable ARC JTAG
1053         IFX_MEI_LongWordRead ((u32) LTQ_RCU_RST, &reg_data);
1054         IFX_MEI_LongWordWrite ((u32) LTQ_RCU_RST, reg_data | LTQ_RCU_RST_REQ_ARC_JTAG);
1055                 break;
1056         case 0:
1057         default:
1058                 break;
1059         }
1060 jtag_end:
1061         if (meierr)
1062                 return DSL_DEV_MEI_ERR_FAILURE;
1063 */
1064
1065         return DSL_DEV_MEI_ERR_SUCCESS;
1066 };
1067
1068 /**
1069  * Enable DFE to MIPS interrupt
1070  * This function enable DFE to MIPS interrupt
1071  *
1072  * \param       pDev            the device pointer
1073  * \param       enable          enable or disable
1074  * \return      DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE
1075  * \ingroup     Internal
1076  */
1077 static DSL_DEV_MeiError_t
1078 IFX_MEI_AdslMailboxIRQEnable (DSL_DEV_Device_t *pDev, int enable)
1079 {
1080         DSL_DEV_MeiError_t meierr;
1081         switch (enable) {
1082         case 0:
1083                 meierr = DSL_DEV_MEI_ERR_SUCCESS;
1084                 IFX_MEI_IRQDisable (pDev);
1085                 break;
1086         case 1:
1087                 IFX_MEI_IRQEnable (pDev);
1088                 meierr = DSL_DEV_MEI_ERR_SUCCESS;
1089                 break;
1090         default:
1091                 meierr = DSL_DEV_MEI_ERR_FAILURE;
1092                 break;
1093
1094         }
1095         return meierr;
1096 }
1097
1098 /**
1099  * Get the modem status
1100  * This function return the modem status
1101  *
1102  * \param       pDev            the device pointer
1103  * \return      1: modem ready 0: not ready
1104  * \ingroup     Internal
1105  */
1106 static int
1107 IFX_MEI_IsModemReady (DSL_DEV_Device_t * pDev)
1108 {
1109         return DSL_DEV_PRIVATE(pDev)->modem_ready;
1110 }
1111
1112 DSL_DEV_MeiError_t
1113 DSL_BSP_AdslLedInit (DSL_DEV_Device_t * dev,
1114                           DSL_DEV_LedId_t led_number,
1115                           DSL_DEV_LedType_t type,
1116                           DSL_DEV_LedHandler_t handler)
1117 {
1118 #if 0
1119         struct led_config_param param;
1120         if (led_number == DSL_LED_LINK_ID && type == DSL_LED_LINK_TYPE && handler == /*DSL_LED_HD_CPU*/DSL_LED_HD_FW) {
1121                 param.operation_mask = CONFIG_OPERATION_UPDATE_SOURCE;
1122                 param.led = 0x01;
1123                 param.source = 0x01;
1124 //                bsp_led_config (&param);
1125
1126         } else if (led_number == DSL_LED_DATA_ID && type == DSL_LED_DATA_TYPE && (handler == DSL_LED_HD_FW)) {
1127                 param.operation_mask = CONFIG_OPERATION_UPDATE_SOURCE;
1128                 param.led = 0x02;
1129                 param.source = 0x02;
1130 //                bsp_led_config (&param);
1131         }
1132 #endif
1133         return DSL_DEV_MEI_ERR_SUCCESS;
1134 };
1135 #if 0
1136 DSL_DEV_MeiError_t
1137 DSL_BSP_AdslLedSet (DSL_DEV_Device_t * dev, DSL_DEV_LedId_t led_number, DSL_DEV_LedMode_t mode)
1138 {
1139         printk(KERN_INFO "[%s %d]: mode = %#x, led_number = %d\n", __func__, __LINE__, mode, led_number);
1140         switch (mode) {
1141         case DSL_LED_OFF:
1142                 switch (led_number) {
1143                 case DSL_LED_LINK_ID:
1144 #ifdef CONFIG_BSP_LED
1145                         bsp_led_set_blink (1, 0);
1146                         bsp_led_set_data (1, 0);
1147 #endif
1148                         break;
1149                 case DSL_LED_DATA_ID:
1150 #ifdef CONFIG_BSP_LED
1151                         bsp_led_set_blink (0, 0);
1152                         bsp_led_set_data (0, 0);
1153 #endif
1154                         break;
1155                 }
1156                 break;
1157         case DSL_LED_FLASH:
1158                 switch (led_number) {
1159                 case DSL_LED_LINK_ID:
1160 #ifdef CONFIG_BSP_LED
1161                         bsp_led_set_blink (1, 1);       // data
1162 #endif
1163                         break;
1164                 case DSL_LED_DATA_ID:
1165 #ifdef CONFIG_BSP_LED
1166                         bsp_led_set_blink (0, 1);       // data
1167 #endif
1168                         break;
1169                 }
1170                 break;
1171         case DSL_LED_ON:
1172                 switch (led_number) {
1173                 case DSL_LED_LINK_ID:
1174 #ifdef CONFIG_BSP_LED
1175                         bsp_led_set_blink (1, 0);
1176                         bsp_led_set_data (1, 1);
1177 #endif
1178                         break;
1179                 case DSL_LED_DATA_ID:
1180 #ifdef CONFIG_BSP_LED
1181                         bsp_led_set_blink (0, 0);
1182                         bsp_led_set_data (0, 1);
1183 #endif
1184                         break;
1185                 }
1186                 break;
1187         }
1188         return DSL_DEV_MEI_ERR_SUCCESS;
1189 };
1190
1191 #endif
1192
1193 /**
1194 * Compose a message.
1195 * This function compose a message from opcode, group, address, index, size, and data
1196 *
1197 * \param       opcode          The message opcode
1198 * \param       group           The message group number
1199 * \param       address         The message address.
1200 * \param       index           The message index.
1201 * \param       size            The number of words to read/write.
1202 * \param       data            The pointer to data.
1203 * \param       CMVMSG          The pointer to message buffer.
1204 * \ingroup     Internal
1205 */
1206 void
1207 makeCMV (u8 opcode, u8 group, u16 address, u16 index, int size, u16 * data, u16 *CMVMSG)
1208 {
1209         memset (CMVMSG, 0, MSG_LENGTH * 2);
1210         CMVMSG[0] = (opcode << 4) + (size & 0xf);
1211         CMVMSG[1] = (((index == 0) ? 0 : 1) << 7) + (group & 0x7f);
1212         CMVMSG[2] = address;
1213         CMVMSG[3] = index;
1214         if (opcode == H2D_CMV_WRITE)
1215                 memcpy (CMVMSG + 4, data, size * 2);
1216         return;
1217 }
1218
1219 /**
1220  * Send a message to ARC and read the response
1221  * This function sends a message to arc, waits the response, and reads the responses.
1222  *
1223  * \param       pDev            the device pointer
1224  * \param       request         Pointer to the request
1225  * \param       reply           Wait reply or not.
1226  * \param       response        Pointer to the response
1227  * \return      DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE
1228  * \ingroup     Internal
1229  */
1230 DSL_DEV_MeiError_t
1231 DSL_BSP_SendCMV (DSL_DEV_Device_t * pDev, u16 * request, int reply, u16 * response)     // write cmv to arc, if reply needed, wait for reply
1232 {
1233         DSL_DEV_MeiError_t meierror;
1234 #if defined(BSP_PORT_RTEMS)
1235         int delay_counter = 0;
1236 #endif
1237
1238         if (MEI_MUTEX_LOCK (DSL_DEV_PRIVATE(pDev)->mei_cmv_sema))
1239                 return -ERESTARTSYS;
1240
1241         DSL_DEV_PRIVATE(pDev)->cmv_reply = reply;
1242         memset (DSL_DEV_PRIVATE(pDev)->CMV_RxMsg, 0,
1243                 sizeof (DSL_DEV_PRIVATE(pDev)->
1244                         CMV_RxMsg));
1245         DSL_DEV_PRIVATE(pDev)->arcmsgav = 0;
1246
1247         meierror = IFX_MEI_MailboxWrite (pDev, request, MSG_LENGTH);
1248
1249         if (meierror != DSL_DEV_MEI_ERR_SUCCESS) {
1250                 DSL_DEV_PRIVATE(pDev)->cmv_waiting = 0;
1251                 DSL_DEV_PRIVATE(pDev)->arcmsgav = 0;
1252                 IFX_MEI_EMSG ("MailboxWrite Fail!\n");
1253                 IFX_MEI_EMSG ("Resetting ARC...\n");
1254                 IFX_MEI_ResetARC(pDev);
1255                 MEI_MUTEX_UNLOCK (DSL_DEV_PRIVATE(pDev)->mei_cmv_sema);
1256                 return meierror;
1257         }
1258         else {
1259                 DSL_DEV_PRIVATE(pDev)->cmv_count++;
1260         }
1261
1262         if (DSL_DEV_PRIVATE(pDev)->cmv_reply ==
1263             NO_REPLY) {
1264                 MEI_MUTEX_UNLOCK (DSL_DEV_PRIVATE(pDev)->mei_cmv_sema);
1265                 return DSL_DEV_MEI_ERR_SUCCESS;
1266         }
1267
1268 #if !defined(BSP_PORT_RTEMS)
1269         if (DSL_DEV_PRIVATE(pDev)->arcmsgav == 0)
1270                 MEI_WAIT_EVENT_TIMEOUT (DSL_DEV_PRIVATE(pDev)->wait_queue_arcmsgav, CMV_TIMEOUT);
1271 #else
1272         while (DSL_DEV_PRIVATE(pDev)->arcmsgav == 0 && delay_counter < CMV_TIMEOUT / 5) {
1273                 MEI_WAIT (5);
1274                 delay_counter++;
1275         }
1276 #endif
1277
1278         DSL_DEV_PRIVATE(pDev)->cmv_waiting = 0;
1279         if (DSL_DEV_PRIVATE(pDev)->arcmsgav == 0) {     //CMV_timeout
1280                 DSL_DEV_PRIVATE(pDev)->arcmsgav = 0;
1281                 IFX_MEI_EMSG ("\%s: DSL_DEV_MEI_ERR_MAILBOX_TIMEOUT\n",
1282                                     __FUNCTION__);
1283                 MEI_MUTEX_UNLOCK (DSL_DEV_PRIVATE(pDev)->mei_cmv_sema);
1284                 return DSL_DEV_MEI_ERR_MAILBOX_TIMEOUT;
1285         }
1286         else {
1287                 DSL_DEV_PRIVATE(pDev)->arcmsgav = 0;
1288                 DSL_DEV_PRIVATE(pDev)->
1289                         reply_count++;
1290                 memcpy (response, DSL_DEV_PRIVATE(pDev)->CMV_RxMsg, MSG_LENGTH * 2);
1291                 MEI_MUTEX_UNLOCK (DSL_DEV_PRIVATE(pDev)->mei_cmv_sema);
1292                 return DSL_DEV_MEI_ERR_SUCCESS;
1293         }
1294         MEI_MUTEX_UNLOCK (DSL_DEV_PRIVATE(pDev)->mei_cmv_sema);
1295         return DSL_DEV_MEI_ERR_SUCCESS;
1296 }
1297
1298 /**
1299  * Reset the ARC, download boot codes, and run the ARC.
1300  * This function resets the ARC, downloads boot codes to ARC, and runs the ARC.
1301  *
1302  * \param       pDev            the device pointer
1303  * \return      DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE
1304  * \ingroup     Internal
1305  */
1306 static DSL_DEV_MeiError_t
1307 IFX_MEI_RunAdslModem (DSL_DEV_Device_t *pDev)
1308 {
1309         int nSize = 0, idx = 0;
1310         uint32_t im0_register, im2_register;
1311 //      DSL_DEV_WinHost_Message_t m;
1312
1313         if (mei_arc_swap_buff == NULL) {
1314                 mei_arc_swap_buff =
1315                         (u32 *) kmalloc (MAXSWAPSIZE * 4, GFP_KERNEL);
1316                 if (mei_arc_swap_buff == NULL) {
1317                         IFX_MEI_EMSG (">>> malloc fail for codeswap buff!!! <<<\n");
1318                         return DSL_DEV_MEI_ERR_FAILURE;
1319                 }
1320                 IFX_MEI_DMSG("allocate %dKB swap buff memory at: 0x%p\n", ksize(mei_arc_swap_buff)/1024, mei_arc_swap_buff);
1321         }
1322
1323         DSL_DEV_PRIVATE(pDev)->img_hdr =
1324                 (ARC_IMG_HDR *) DSL_DEV_PRIVATE(pDev)->adsl_mem_info[0].address;
1325         if ((DSL_DEV_PRIVATE(pDev)->img_hdr->
1326              count) * sizeof (ARC_SWP_PAGE_HDR) > SDRAM_SEGMENT_SIZE) {
1327                 IFX_MEI_EMSG ("firmware header size is bigger than 64K segment size\n");
1328                 return DSL_DEV_MEI_ERR_FAILURE;
1329         }
1330         // check image size
1331         for (idx = 0; idx < MAX_BAR_REGISTERS; idx++) {
1332                 nSize += DSL_DEV_PRIVATE(pDev)->adsl_mem_info[idx].nCopy;
1333         }
1334         if (nSize !=
1335             DSL_DEV_PRIVATE(pDev)->image_size) {
1336                 IFX_MEI_EMSG ("Firmware download is not completed. Please download firmware again!\n");
1337                 return DSL_DEV_MEI_ERR_FAILURE;
1338         }
1339         // TODO: check crc
1340         ///
1341
1342         IFX_MEI_ResetARC (pDev);
1343         IFX_MEI_HaltArc (pDev);
1344         IFX_MEI_BarUpdate (pDev, DSL_DEV_PRIVATE(pDev)->nBar);
1345
1346         //IFX_MEI_DMSG("Starting to meiDownloadBootCode\n");
1347
1348         IFX_MEI_DownloadBootCode (pDev);
1349
1350         im0_register = (*LTQ_ICU_IM0_IER) & (1 << 20);
1351         im2_register = (*LTQ_ICU_IM2_IER) & (1 << 20);
1352         /* Turn off irq */
1353         #ifdef CONFIG_SOC_AMAZON_SE
1354 #define IFXMIPS_USB_OC_INT0 (INT_NUM_IM4_IRL0 + 23)
1355         disable_irq (IFXMIPS_USB_OC_INT0);
1356 //      disable_irq (IFXMIPS_USB_OC_INT2);
1357         #elif defined(CONFIG_SOC_AR9)
1358 #define IFXMIPS_USB_OC_INT0 (INT_NUM_IM4_IRL1 + 28)
1359         disable_irq (IFXMIPS_USB_OC_INT0);
1360 //      disable_irq (IFXMIPS_USB_OC_INT2);
1361         #elif defined(CONFIG_SOC_XWAY)
1362         disable_irq (LTQ_USB_OC_INT);
1363         #else
1364         #error unkonwn arch
1365         #endif
1366         disable_irq (pDev->nIrq[IFX_DYING_GASP]);
1367
1368         IFX_MEI_RunArc (pDev);
1369
1370         MEI_WAIT_EVENT_TIMEOUT (DSL_DEV_PRIVATE(pDev)->wait_queue_modemready, 1000);
1371
1372         #ifdef CONFIG_SOC_AMAZON_SE
1373         MEI_MASK_AND_ACK_IRQ (IFXMIPS_USB_OC_INT0);
1374 //      MEI_MASK_AND_ACK_IRQ (IFXMIPS_USB_OC_INT2);
1375         #elif defined(CONFIG_SOC_AR9)
1376         MEI_MASK_AND_ACK_IRQ (IFXMIPS_USB_OC_INT0);
1377 //      MEI_MASK_AND_ACK_IRQ (IFXMIPS_USB_OC_INT2);
1378         #elif defined(CONFIG_SOC_XWAY)
1379         MEI_MASK_AND_ACK_IRQ (LTQ_USB_OC_INT);
1380         #else
1381         #error unkonwn arch
1382         #endif
1383         MEI_MASK_AND_ACK_IRQ (pDev->nIrq[IFX_DYING_GASP]);
1384
1385         /* Re-enable irq */
1386         enable_irq(pDev->nIrq[IFX_DYING_GASP]);
1387         *LTQ_ICU_IM0_IER |= im0_register;
1388         *LTQ_ICU_IM2_IER |= im2_register;
1389
1390         if (DSL_DEV_PRIVATE(pDev)->modem_ready != 1) {
1391                 IFX_MEI_EMSG ("Modem failed to be ready!\n");
1392                 return DSL_DEV_MEI_ERR_FAILURE;
1393         } else {
1394                 IFX_MEI_DMSG("Modem is ready.\n");
1395                 return DSL_DEV_MEI_ERR_SUCCESS;
1396         }
1397 }
1398
1399 /**
1400  * Get the page's data pointer
1401  * This function caculats the data address from the firmware header.
1402  *
1403  * \param       pDev            the device pointer
1404  * \param       Page            The page number.
1405  * \param       data            Data page or program page.
1406  * \param       MaxSize         The maximum size to read.
1407  * \param       Buffer          Pointer to data.
1408  * \param       Dest            Pointer to the destination address.
1409  * \return      The number of bytes to read.
1410  * \ingroup     Internal
1411  */
1412 static int
1413 IFX_MEI_GetPage (DSL_DEV_Device_t * pDev, u32 Page, u32 data,
1414                        u32 MaxSize, u32 * Buffer, u32 * Dest)
1415 {
1416         u32 size;
1417         u32 i;
1418         u32 *p;
1419         u32 idx, offset, nBar = 0;
1420
1421         if (Page > DSL_DEV_PRIVATE(pDev)->img_hdr->count)
1422                 return -2;
1423         /*
1424          **     Get program or data size, depending on "data" flag
1425          */
1426         size = (data == GET_DATA) ? (DSL_DEV_PRIVATE(pDev)->img_hdr->page[Page].d_size) :
1427                              (DSL_DEV_PRIVATE(pDev)->img_hdr->page[Page].p_size);
1428         size &= BOOT_FLAG_MASK; //      Clear boot bit!
1429         if (size > MaxSize)
1430                 return -1;
1431
1432         if (size == 0)
1433                 return 0;
1434         /*
1435          **     Get program or data offset, depending on "data" flag
1436          */
1437         i = data ? (DSL_DEV_PRIVATE(pDev)->img_hdr->page[Page].d_offset) :
1438                         (DSL_DEV_PRIVATE(pDev)->img_hdr->page[Page].p_offset);
1439
1440         /*
1441          **     Copy data/program to buffer
1442          */
1443
1444         idx = i / SDRAM_SEGMENT_SIZE;
1445         offset = i % SDRAM_SEGMENT_SIZE;
1446         p = (u32 *) ((u8 *) DSL_DEV_PRIVATE(pDev)->adsl_mem_info[idx].address + offset);
1447
1448         for (i = 0; i < size; i++) {
1449                 if (offset + i * 4 - (nBar * SDRAM_SEGMENT_SIZE) >= SDRAM_SEGMENT_SIZE) {
1450                         idx++;
1451                         nBar++;
1452                         p = (u32 *) ((u8 *) KSEG1ADDR ((u32)DSL_DEV_PRIVATE(pDev)->adsl_mem_info[idx].address));
1453                 }
1454                 Buffer[i] = *p++;
1455         }
1456
1457         /*
1458          **     Pass back data/program destination address
1459          */
1460         *Dest = data ? (DSL_DEV_PRIVATE(pDev)-> img_hdr->page[Page].d_dest) :
1461                                 (DSL_DEV_PRIVATE(pDev)->img_hdr->page[Page].p_dest);
1462
1463         return size;
1464 }
1465
1466 /**
1467  * Free the memory for ARC firmware
1468  *
1469  * \param       pDev            the device pointer
1470  * \param       type    Free all memory or free the unused memory after showtime
1471  * \ingroup     Internal
1472  */
1473 const char *free_str[4] = {"Invalid", "Free_Reload", "Free_Showtime", "Free_All"};
1474 static int
1475 IFX_MEI_DFEMemoryFree (DSL_DEV_Device_t * pDev, int type)
1476 {
1477         int idx = 0;
1478         smmu_mem_info_t *adsl_mem_info =
1479                 DSL_DEV_PRIVATE(pDev)->adsl_mem_info;
1480
1481         for (idx = 0; idx < MAX_BAR_REGISTERS; idx++) {
1482                 if (type == FREE_ALL ||adsl_mem_info[idx].type == type) {
1483                         if (adsl_mem_info[idx].size > 0) {
1484                                 IFX_MEI_DMSG ("Freeing memory %p (%s)\n", adsl_mem_info[idx].org_address, free_str[adsl_mem_info[idx].type]);
1485                                 if ( idx == XDATA_REGISTER ) {
1486                                     g_xdata_addr = NULL;
1487                                     if ( ifx_mei_atm_showtime_exit )
1488                                         ifx_mei_atm_showtime_exit();
1489                                 }
1490                                 kfree (adsl_mem_info[idx].org_address);
1491                                 adsl_mem_info[idx].org_address = 0;
1492                                 adsl_mem_info[idx].address = 0;
1493                                 adsl_mem_info[idx].size = 0;
1494                                 adsl_mem_info[idx].type = 0;
1495                                 adsl_mem_info[idx].nCopy = 0;
1496                         }
1497                 }
1498         }
1499
1500         if(mei_arc_swap_buff != NULL){
1501                 IFX_MEI_DMSG("free %dKB swap buff memory at: 0x%p\n", ksize(mei_arc_swap_buff)/1024, mei_arc_swap_buff);
1502                 kfree(mei_arc_swap_buff);
1503                 mei_arc_swap_buff=NULL;
1504         }
1505
1506         return 0;
1507 }
1508 static int
1509 IFX_MEI_DFEMemoryAlloc (DSL_DEV_Device_t * pDev, long size)
1510 {
1511         unsigned long mem_ptr;
1512         char *org_mem_ptr = NULL;
1513         int idx = 0;
1514         long total_size = 0;
1515         int err = 0;
1516         smmu_mem_info_t *adsl_mem_info =
1517                 ((ifx_mei_device_private_t *) pDev->pPriv)->adsl_mem_info;
1518 //              DSL_DEV_PRIVATE(pDev)->adsl_mem_info;
1519         int allocate_size = SDRAM_SEGMENT_SIZE;
1520
1521         IFX_MEI_DMSG("image_size = %ld\n", size);
1522         // Alloc Swap Pages
1523         for (idx = 0; size > 0 && idx < MAX_BAR_REGISTERS; idx++) {
1524                 // skip bar15 for XDATA usage.
1525                 if (idx == XDATA_REGISTER)
1526                         continue;
1527 #if 0
1528                 if (size < SDRAM_SEGMENT_SIZE) {
1529                         allocate_size = size;
1530                         if (allocate_size < 1024)
1531                                 allocate_size = 1024;
1532                 }
1533 #endif
1534                 if (idx == (MAX_BAR_REGISTERS - 1))
1535                         allocate_size = size;
1536                 else
1537                         allocate_size = SDRAM_SEGMENT_SIZE;
1538                 org_mem_ptr = kmalloc (allocate_size + 1024, GFP_KERNEL);
1539                 if (org_mem_ptr == NULL) {
1540                         IFX_MEI_EMSG ("%d: kmalloc %d bytes memory fail!\n", idx, allocate_size);
1541                         err = -ENOMEM;
1542                         goto allocate_error;
1543                 }
1544                 mem_ptr = (unsigned long) (org_mem_ptr + 1023) & ~(1024 -1);
1545                 adsl_mem_info[idx].address = (char *) mem_ptr;
1546                 adsl_mem_info[idx].org_address = org_mem_ptr;
1547                 adsl_mem_info[idx].size = allocate_size;
1548                 size -= allocate_size;
1549                 total_size += allocate_size;
1550         }
1551         if (size > 0) {
1552                 IFX_MEI_EMSG ("Image size is too large!\n");
1553                 err = -EFBIG;
1554                 goto allocate_error;
1555         }
1556         err = idx;
1557         return err;
1558
1559       allocate_error:
1560         IFX_MEI_DFEMemoryFree (pDev, FREE_ALL);
1561         return err;
1562 }
1563
1564 /**
1565  * Program the BAR registers
1566  *
1567  * \param       pDev            the device pointer
1568  * \param       nTotalBar       The number of bar to program.
1569  * \ingroup     Internal
1570  */
1571 static int
1572 IFX_MEI_BarUpdate (DSL_DEV_Device_t * pDev, int nTotalBar)
1573 {
1574         int idx = 0;
1575         smmu_mem_info_t *adsl_mem_info =
1576                 DSL_DEV_PRIVATE(pDev)->adsl_mem_info;
1577
1578         for (idx = 0; idx < nTotalBar; idx++) {
1579                 //skip XDATA register
1580                 if (idx == XDATA_REGISTER)
1581                         continue;
1582                 IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_XMEM_BAR_BASE + idx * 4,
1583                         (((uint32_t) adsl_mem_info[idx].address) & 0x0FFFFFFF));
1584         }
1585         for (idx = nTotalBar; idx < MAX_BAR_REGISTERS; idx++) {
1586                 if (idx == XDATA_REGISTER)
1587                         continue;
1588                 IFX_MEI_LongWordWriteOffset (pDev,  (u32) ME_XMEM_BAR_BASE  + idx * 4,
1589                          (((uint32_t)adsl_mem_info[nTotalBar - 1].address) & 0x0FFFFFFF));
1590                 /* These are for /proc/danube_mei/meminfo purpose */
1591                 adsl_mem_info[idx].address = adsl_mem_info[nTotalBar - 1].address;
1592                 adsl_mem_info[idx].org_address = adsl_mem_info[nTotalBar - 1].org_address;
1593                 adsl_mem_info[idx].size = 0; /* Prevent it from being freed */
1594         }
1595
1596     g_xdata_addr = adsl_mem_info[XDATA_REGISTER].address;
1597         IFX_MEI_LongWordWriteOffset (pDev,  (u32) ME_XMEM_BAR_BASE  + XDATA_REGISTER * 4,
1598                 (((uint32_t) adsl_mem_info [XDATA_REGISTER].address) & 0x0FFFFFFF));
1599         // update MEI_XDATA_BASE_SH
1600         IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_XDATA_BASE_SH,
1601                  ((unsigned long)adsl_mem_info[XDATA_REGISTER].address) & 0x0FFFFFFF);
1602
1603         return DSL_DEV_MEI_ERR_SUCCESS;
1604 }
1605
1606 /* This copies the firmware from secondary storage to 64k memory segment in SDRAM */
1607 DSL_DEV_MeiError_t
1608 DSL_BSP_FWDownload (DSL_DEV_Device_t * pDev, const char *buf,
1609                          unsigned long size, long *loff, long *current_offset)
1610 {
1611         ARC_IMG_HDR img_hdr_tmp;
1612         smmu_mem_info_t *adsl_mem_info = DSL_DEV_PRIVATE(pDev)->adsl_mem_info;
1613
1614         size_t nRead = 0, nCopy = 0;
1615         char *mem_ptr;
1616         ssize_t retval = -ENOMEM;
1617         int idx = 0;
1618
1619         IFX_MEI_DMSG("\n");
1620
1621         if (*loff == 0) {
1622                 if (size < sizeof (img_hdr_tmp)) {
1623                         IFX_MEI_EMSG ("Firmware size is too small!\n");
1624                         return retval;
1625                 }
1626                 copy_from_user ((char *) &img_hdr_tmp, buf, sizeof (img_hdr_tmp));
1627                 // header of image_size and crc are not included.
1628                 DSL_DEV_PRIVATE(pDev)->image_size = le32_to_cpu (img_hdr_tmp.size) + 8;
1629
1630                 if (DSL_DEV_PRIVATE(pDev)->image_size > 1024 * 1024) {
1631                         IFX_MEI_EMSG ("Firmware size is too large!\n");
1632                         return retval;
1633                 }
1634                 // check if arc is halt
1635                 IFX_MEI_ResetARC (pDev);
1636                 IFX_MEI_HaltArc (pDev);
1637
1638                 IFX_MEI_DFEMemoryFree (pDev, FREE_ALL); //free all
1639
1640                 retval = IFX_MEI_DFEMemoryAlloc (pDev,  DSL_DEV_PRIVATE(pDev)->image_size);
1641                 if (retval < 0) {
1642                         IFX_MEI_EMSG ("Error: No memory space left.\n");
1643                         goto error;
1644                 }
1645                 for (idx = 0; idx < retval; idx++) {
1646                         //skip XDATA register
1647                         if (idx == XDATA_REGISTER)
1648                                 continue;
1649                         if (idx * SDRAM_SEGMENT_SIZE < le32_to_cpu (img_hdr_tmp.page[0].p_offset))
1650                                 adsl_mem_info[idx].type = FREE_RELOAD;
1651                         else
1652                                 adsl_mem_info[idx].type = FREE_SHOWTIME;
1653                 }
1654                 DSL_DEV_PRIVATE(pDev)->nBar = retval;
1655
1656                 DSL_DEV_PRIVATE(pDev)->img_hdr =
1657                         (ARC_IMG_HDR *) adsl_mem_info[0].address;
1658
1659                 adsl_mem_info[XDATA_REGISTER].org_address = kmalloc (SDRAM_SEGMENT_SIZE + 1024, GFP_KERNEL);
1660                 adsl_mem_info[XDATA_REGISTER].address =
1661                         (char *) ((unsigned long) (adsl_mem_info[XDATA_REGISTER].org_address + 1023) & 0xFFFFFC00);
1662
1663                 adsl_mem_info[XDATA_REGISTER].size = SDRAM_SEGMENT_SIZE;
1664
1665                 if (adsl_mem_info[XDATA_REGISTER].address == NULL) {
1666                         IFX_MEI_EMSG ("kmalloc memory fail!\n");
1667                         retval = -ENOMEM;
1668                         goto error;
1669                 }
1670                 adsl_mem_info[XDATA_REGISTER].type = FREE_RELOAD;
1671                 IFX_MEI_DMSG("-> IFX_MEI_BarUpdate()\n");
1672                 IFX_MEI_BarUpdate (pDev, (DSL_DEV_PRIVATE(pDev)->nBar));
1673         }
1674         else if (DSL_DEV_PRIVATE(pDev)-> image_size == 0) {
1675                 IFX_MEI_EMSG ("Error: Firmware size=0! \n");
1676                 goto error;
1677         }
1678
1679         nRead = 0;
1680         while (nRead < size) {
1681                 long offset = ((long) (*loff) + nRead) % SDRAM_SEGMENT_SIZE;
1682                 idx = (((long) (*loff)) + nRead) / SDRAM_SEGMENT_SIZE;
1683                 mem_ptr = (char *) KSEG1ADDR ((unsigned long) (adsl_mem_info[idx].address) + offset);
1684                 if ((size - nRead + offset) > SDRAM_SEGMENT_SIZE)
1685                         nCopy = SDRAM_SEGMENT_SIZE - offset;
1686                 else
1687                         nCopy = size - nRead;
1688                 copy_from_user (mem_ptr, buf + nRead, nCopy);
1689                 for (offset = 0; offset < (nCopy / 4); offset++) {
1690                         ((unsigned long *) mem_ptr)[offset] = le32_to_cpu (((unsigned long *) mem_ptr)[offset]);
1691                 }
1692                 nRead += nCopy;
1693                 adsl_mem_info[idx].nCopy += nCopy;
1694         }
1695
1696         *loff += size;
1697         *current_offset = size;
1698         return DSL_DEV_MEI_ERR_SUCCESS;
1699 error:
1700         IFX_MEI_DFEMemoryFree (pDev, FREE_ALL);
1701         return DSL_DEV_MEI_ERR_FAILURE;
1702 }
1703 /*
1704  * Register a callback event.
1705  * Return:
1706  * -1 if the event already has a callback function registered.
1707  *  0 success
1708  */
1709 int DSL_BSP_EventCBRegister(DSL_BSP_EventCallBack_t *p)
1710 {
1711         if (!p) {
1712                 IFX_MEI_EMSG("Invalid parameter!\n");
1713                 return -EINVAL;
1714         }
1715         if (p->event > DSL_BSP_CB_LAST || p->event < DSL_BSP_CB_FIRST) {
1716                 IFX_MEI_EMSG("Invalid Event %d\n", p->event);
1717                 return -EINVAL;
1718         }
1719         if (dsl_bsp_event_callback[p->event].function) {
1720                 IFX_MEI_EMSG("Event %d already has a callback function registered!\n", p->event);
1721                 return -1;
1722         } else {
1723                 dsl_bsp_event_callback[p->event].function = p->function;
1724                 dsl_bsp_event_callback[p->event].event    = p->event;
1725                 dsl_bsp_event_callback[p->event].pData    = p->pData;
1726         }
1727         return 0;
1728 }
1729 int DSL_BSP_EventCBUnregister(DSL_BSP_EventCallBack_t *p)
1730 {
1731         if (!p) {
1732                 IFX_MEI_EMSG("Invalid parameter!\n");
1733                 return -EINVAL;
1734         }
1735         if (p->event > DSL_BSP_CB_LAST || p->event < DSL_BSP_CB_FIRST) {
1736                 IFX_MEI_EMSG("Invalid Event %d\n", p->event);
1737                 return -EINVAL;
1738         }
1739         if (dsl_bsp_event_callback[p->event].function) {
1740                 IFX_MEI_EMSG("Unregistering Event %d...\n", p->event);
1741                 dsl_bsp_event_callback[p->event].function = NULL;
1742                 dsl_bsp_event_callback[p->event].pData    = NULL;
1743         } else {
1744                 IFX_MEI_EMSG("Event %d is not registered!\n", p->event);
1745                 return -1;
1746         }
1747         return 0;
1748 }
1749
1750 /**
1751  * MEI Dying Gasp interrupt handler
1752  *
1753  * \param int1
1754  * \param void0
1755  * \param regs  Pointer to the structure of danube mips registers
1756  * \ingroup     Internal
1757  */
1758 static irqreturn_t IFX_MEI_Dying_Gasp_IrqHandle (int int1, void *void0)
1759 {
1760         DSL_DEV_Device_t *pDev = (DSL_DEV_Device_t *) void0;
1761         DSL_BSP_CB_Type_t event;
1762
1763         if (pDev == NULL)
1764                 IFX_MEI_EMSG("Error: Got Interrupt but pDev is NULL!!!!\n");
1765
1766 #ifndef CONFIG_SMP
1767         disable_irq (pDev->nIrq[IFX_DYING_GASP]);
1768 #else
1769         disable_irq_nosync(pDev->nIrq[IFX_DYING_GASP]);
1770 #endif
1771         event = DSL_BSP_CB_DYING_GASP;
1772
1773         if (dsl_bsp_event_callback[event].function)
1774                 (*dsl_bsp_event_callback[event].function)(pDev, event, dsl_bsp_event_callback[event].pData);
1775
1776 #ifdef CONFIG_USE_EMULATOR
1777     IFX_MEI_EMSG("Dying Gasp! Shutting Down... (Work around for Amazon-S Venus emulator)\n");
1778 #else
1779         IFX_MEI_EMSG("Dying Gasp! Shutting Down...\n");
1780 //      kill_proc (1, SIGINT, 1);       /* Ask init to reboot us */
1781 #endif
1782         return IRQ_HANDLED;
1783 }
1784
1785 extern void ifx_usb_enable_afe_oc(void);
1786
1787 /**
1788  * MEI interrupt handler
1789  *
1790  * \param int1
1791  * \param void0
1792  * \param regs  Pointer to the structure of danube mips registers
1793  * \ingroup     Internal
1794  */
1795 static irqreturn_t IFX_MEI_IrqHandle (int int1, void *void0)
1796 {
1797         u32 scratch;
1798         DSL_DEV_Device_t *pDev = (DSL_DEV_Device_t *) void0;
1799 #if defined(CONFIG_LTQ_MEI_FW_LOOPBACK) && defined(DFE_PING_TEST)
1800         dfe_loopback_irq_handler (pDev);
1801         return IRQ_HANDLED;
1802 #endif //CONFIG_AMAZON_S_MEI_FW_LOOPBACK
1803         DSL_BSP_CB_Type_t event;
1804
1805         if (pDev == NULL)
1806                 IFX_MEI_EMSG("Error: Got Interrupt but pDev is NULL!!!!\n");
1807
1808         IFX_MEI_DebugRead (pDev, ARC_MEI_MAILBOXR, &scratch, 1);
1809         if (scratch & OMB_CODESWAP_MESSAGE_MSG_TYPE_MASK) {
1810                 IFX_MEI_EMSG("Receive Code Swap Request interrupt!!!\n");
1811                 return IRQ_HANDLED;
1812         }
1813         else if (scratch & OMB_CLEAREOC_INTERRUPT_CODE)  {
1814                 // clear eoc message interrupt
1815                 IFX_MEI_DMSG("OMB_CLEAREOC_INTERRUPT_CODE\n");
1816                 event = DSL_BSP_CB_CEOC_IRQ;
1817                 IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_ARC2ME_STAT, ARC_TO_MEI_MSGAV);
1818                 if (dsl_bsp_event_callback[event].function)
1819                         (*dsl_bsp_event_callback[event].function)(pDev, event, dsl_bsp_event_callback[event].pData);
1820         } else if (scratch & OMB_REBOOT_INTERRUPT_CODE) {
1821                 // Reboot
1822                 IFX_MEI_DMSG("OMB_REBOOT_INTERRUPT_CODE\n");
1823                 event = DSL_BSP_CB_FIRMWARE_REBOOT;
1824
1825                 IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_ARC2ME_STAT, ARC_TO_MEI_MSGAV);
1826
1827                 if (dsl_bsp_event_callback[event].function)
1828                         (*dsl_bsp_event_callback[event].function)(pDev, event, dsl_bsp_event_callback[event].pData);
1829         } else { // normal message
1830                 IFX_MEI_MailboxRead (pDev, DSL_DEV_PRIVATE(pDev)->CMV_RxMsg, MSG_LENGTH);
1831                 if (DSL_DEV_PRIVATE(pDev)-> cmv_waiting == 1) {
1832                         DSL_DEV_PRIVATE(pDev)-> arcmsgav = 1;
1833                         DSL_DEV_PRIVATE(pDev)-> cmv_waiting = 0;
1834 #if !defined(BSP_PORT_RTEMS)
1835                         MEI_WAKEUP_EVENT (DSL_DEV_PRIVATE(pDev)->wait_queue_arcmsgav);
1836 #endif
1837                 }
1838                 else {
1839                         DSL_DEV_PRIVATE(pDev)-> modem_ready_cnt++;
1840                         memcpy ((char *) DSL_DEV_PRIVATE(pDev)->Recent_indicator,
1841                                 (char *) DSL_DEV_PRIVATE(pDev)->CMV_RxMsg, MSG_LENGTH * 2);
1842                         if (((DSL_DEV_PRIVATE(pDev)->CMV_RxMsg[0] & 0xff0) >> 4) == D2H_AUTONOMOUS_MODEM_READY_MSG) {
1843                                 //check ARC ready message
1844                                 IFX_MEI_DMSG ("Got MODEM_READY_MSG\n");
1845                                 DSL_DEV_PRIVATE(pDev)->modem_ready = 1;
1846                                 MEI_WAKEUP_EVENT (DSL_DEV_PRIVATE(pDev)->wait_queue_modemready);
1847                         }
1848                 }
1849         }
1850
1851         return IRQ_HANDLED;
1852 }
1853
1854 int
1855 DSL_BSP_ATMLedCBRegister (int (*ifx_adsl_ledcallback) (void))
1856 {
1857     g_adsl_ledcallback = ifx_adsl_ledcallback;
1858     return 0;
1859 }
1860
1861 int
1862 DSL_BSP_ATMLedCBUnregister (int (*ifx_adsl_ledcallback) (void))
1863 {
1864     g_adsl_ledcallback = adsl_dummy_ledcallback;
1865     return 0;
1866 }
1867
1868 #if 0
1869 int
1870 DSL_BSP_EventCBRegister (int (*ifx_adsl_callback)
1871                                 (DSL_BSP_CB_Event_t * param))
1872 {
1873         int error = 0;
1874
1875         if (DSL_EventCB == NULL) {
1876                 DSL_EventCB = ifx_adsl_callback;
1877         }
1878         else {
1879                 error = -EIO;
1880         }
1881         return error;
1882 }
1883
1884 int
1885 DSL_BSP_EventCBUnregister (int (*ifx_adsl_callback)
1886                                   (DSL_BSP_CB_Event_t * param))
1887 {
1888         int error = 0;
1889
1890         if (DSL_EventCB == ifx_adsl_callback) {
1891                 DSL_EventCB = NULL;
1892         }
1893         else {
1894                 error = -EIO;
1895         }
1896         return error;
1897 }
1898
1899 static int
1900 DSL_BSP_GetEventCB (int (**ifx_adsl_callback)
1901                            (DSL_BSP_CB_Event_t * param))
1902 {
1903         *ifx_adsl_callback = DSL_EventCB;
1904         return 0;
1905 }
1906 #endif
1907
1908 #ifdef CONFIG_LTQ_MEI_FW_LOOPBACK
1909 #define mte_reg_base    (0x4800*4+0x20000)
1910
1911 /* Iridia Registers Address Constants */
1912 #define MTE_Reg(r)      (int)(mte_reg_base + (r*4))
1913
1914 #define IT_AMODE        MTE_Reg(0x0004)
1915
1916 #define TIMER_DELAY     (1024)
1917 #define BC0_BYTES       (32)
1918 #define BC1_BYTES       (30)
1919 #define NUM_MB          (12)
1920 #define TIMEOUT_VALUE   2000
1921
1922 static void
1923 BFMWait (u32 cycle)
1924 {
1925         u32 i;
1926         for (i = 0; i < cycle; i++);
1927 }
1928
1929 static void
1930 WriteRegLong (u32 addr, u32 data)
1931 {
1932         //*((volatile u32 *)(addr)) =  data;
1933         IFX_MEI_WRITE_REGISTER_L (data, addr);
1934 }
1935
1936 static u32
1937 ReadRegLong (u32 addr)
1938 {
1939         // u32  rd_val;
1940         //rd_val = *((volatile u32 *)(addr));
1941         // return rd_val;
1942         return IFX_MEI_READ_REGISTER_L (addr);
1943 }
1944
1945 /* This routine writes the mailbox with the data in an input array */
1946 static void
1947 WriteMbox (u32 * mboxarray, u32 size)
1948 {
1949         IFX_MEI_DebugWrite (&dsl_devices[0], IMBOX_BASE, mboxarray, size);
1950         IFX_MEI_DMSG("write to %X\n", IMBOX_BASE);
1951         IFX_MEI_LongWordWriteOffset (&dsl_devices[0], (u32) ME_ME2ARC_INT, MEI_TO_ARC_MSGAV);
1952 }
1953
1954 /* This routine reads the output mailbox and places the results into an array */
1955 static void
1956 ReadMbox (u32 * mboxarray, u32 size)
1957 {
1958         IFX_MEI_DebugRead (&dsl_devices[0], OMBOX_BASE, mboxarray, size);
1959         IFX_MEI_DMSG("read from %X\n", OMBOX_BASE);
1960 }
1961
1962 static void
1963 MEIWriteARCValue (u32 address, u32 value)
1964 {
1965         u32 i, check = 0;
1966
1967         /* Write address register */
1968         IFX_MEI_WRITE_REGISTER_L (address,  ME_DBG_WR_AD + LTQ_MEI_BASE_ADDR);
1969
1970         /* Write data register */
1971         IFX_MEI_WRITE_REGISTER_L (value, ME_DBG_DATA + LTQ_MEI_BASE_ADDR);
1972
1973         /* wait until complete - timeout at 40 */
1974         for (i = 0; i < 40; i++) {
1975                 check = IFX_MEI_READ_REGISTER_L (ME_ARC2ME_STAT + LTQ_MEI_BASE_ADDR);
1976
1977                 if ((check & ARC_TO_MEI_DBG_DONE))
1978                         break;
1979         }
1980         /* clear the flag */
1981         IFX_MEI_WRITE_REGISTER_L (ARC_TO_MEI_DBG_DONE, ME_ARC2ME_STAT + LTQ_MEI_BASE_ADDR);
1982 }
1983
1984 void
1985 arc_code_page_download (uint32_t arc_code_length, uint32_t * start_address)
1986 {
1987         int count;
1988
1989         IFX_MEI_DMSG("try to download pages,size=%d\n", arc_code_length);
1990         IFX_MEI_ControlModeSet (&dsl_devices[0], MEI_MASTER_MODE);
1991         IFX_MEI_HaltArc (&dsl_devices[0]);
1992         IFX_MEI_LongWordWriteOffset (&dsl_devices[0], (u32) ME_DX_AD, 0);
1993         for (count = 0; count < arc_code_length; count++) {
1994                 IFX_MEI_LongWordWriteOffset (&dsl_devices[0], (u32) ME_DX_DATA,
1995                                                    *(start_address + count));
1996         }
1997         IFX_MEI_ControlModeSet (&dsl_devices[0], JTAG_MASTER_MODE);
1998 }
1999 static int
2000 load_jump_table (unsigned long addr)
2001 {
2002         int i;
2003         uint32_t addr_le, addr_be;
2004         uint32_t jump_table[32];
2005
2006         for (i = 0; i < 16; i++) {
2007                 addr_le = i * 8 + addr;
2008                 addr_be = ((addr_le >> 16) & 0xffff);
2009                 addr_be |= ((addr_le & 0xffff) << 16);
2010                 jump_table[i * 2 + 0] = 0x0f802020;
2011                 jump_table[i * 2 + 1] = addr_be;
2012                 //printk("jt %X %08X %08X\n",i,jump_table[i*2+0],jump_table[i*2+1]);
2013         }
2014         arc_code_page_download (32, &jump_table[0]);
2015 return 0;
2016 }
2017
2018 int got_int = 0;
2019
2020 void
2021 dfe_loopback_irq_handler (DSL_DEV_Device_t *pDev)
2022 {
2023         uint32_t rd_mbox[10];
2024
2025         memset (&rd_mbox[0], 0, 10 * 4);
2026         ReadMbox (&rd_mbox[0], 6);
2027         if (rd_mbox[0] == 0x0) {
2028                 FX_MEI_DMSG("Get ARC_ACK\n");
2029                 got_int = 1;
2030         }
2031         else if (rd_mbox[0] == 0x5) {
2032                 IFX_MEI_DMSG("Get ARC_BUSY\n");
2033                 got_int = 2;
2034         }
2035         else if (rd_mbox[0] == 0x3) {
2036                 IFX_MEI_DMSG("Get ARC_EDONE\n");
2037                 if (rd_mbox[1] == 0x0) {
2038                         got_int = 3;
2039                         IFX_MEI_DMSG("Get E_MEMTEST\n");
2040                         if (rd_mbox[2] != 0x1) {
2041                                 got_int = 4;
2042                                 IFX_MEI_DMSG("Get Result %X\n", rd_mbox[2]);
2043                         }
2044                 }
2045         }
2046         IFX_MEI_LongWordWriteOffset (&dsl_devices[0], (u32) ME_ARC2ME_STAT,
2047                 ARC_TO_MEI_DBG_DONE);
2048         MEI_MASK_AND_ACK_IRQ (pDev->nIrq[IFX_DFEIR]);
2049         disable_irq (pDev->nIrq[IFX_DFEIR]);
2050         //got_int = 1;
2051         return;
2052 }
2053
2054 static void
2055 wait_mem_test_result (void)
2056 {
2057         uint32_t mbox[5];
2058         mbox[0] = 0;
2059
2060         IFX_MEI_DMSG("Waiting Starting\n");
2061         while (mbox[0] == 0) {
2062                 ReadMbox (&mbox[0], 5);
2063         }
2064         IFX_MEI_DMSG("Try to get mem test result.\n");
2065         ReadMbox (&mbox[0], 5);
2066         if (mbox[0] == 0xA) {
2067                 IFX_MEI_DMSG("Success.\n");
2068         }
2069         else if (mbox[0] == 0xA) {
2070                 IFX_MEI_EMSG("Fail,address %X,except data %X,receive data %X\n",
2071                         mbox[1], mbox[2], mbox[3]);
2072         }
2073         else {
2074                 IFX_MEI_EMSG("Fail\n");
2075         }
2076 }
2077
2078 static int
2079 arc_ping_testing (DSL_DEV_Device_t *pDev)
2080 {
2081 #define MEI_PING 0x00000001
2082         uint32_t wr_mbox[10], rd_mbox[10];
2083         int i;
2084
2085         for (i = 0; i < 10; i++) {
2086                 wr_mbox[i] = 0;
2087                 rd_mbox[i] = 0;
2088         }
2089
2090         FX_MEI_DMSG("send ping msg\n");
2091         wr_mbox[0] = MEI_PING;
2092         WriteMbox (&wr_mbox[0], 10);
2093
2094         while (got_int == 0) {
2095                 MEI_WAIT (100);
2096         }
2097
2098         IFX_MEI_DMSG("send start event\n");
2099         got_int = 0;
2100
2101         wr_mbox[0] = 0x4;
2102         wr_mbox[1] = 0;
2103         wr_mbox[2] = 0;
2104         wr_mbox[3] = (uint32_t) 0xf5acc307e;
2105         wr_mbox[4] = 5;
2106         wr_mbox[5] = 2;
2107         wr_mbox[6] = 0x1c000;
2108         wr_mbox[7] = 64;
2109         wr_mbox[8] = 0;
2110         wr_mbox[9] = 0;
2111         WriteMbox (&wr_mbox[0], 10);
2112         DSL_ENABLE_IRQ (pDev->nIrq[IFX_DFEIR]);
2113         //printk("IFX_MEI_MailboxWrite ret=%d\n",i);
2114         IFX_MEI_LongWordWriteOffset (&dsl_devices[0],
2115                                            (u32) ME_ME2ARC_INT,
2116                                            MEI_TO_ARC_MSGAV);
2117         IFX_MEI_DMSG("sleeping\n");
2118         while (1) {
2119                 if (got_int > 0) {
2120
2121                         if (got_int > 3)
2122                                 IFX_MEI_DMSG("got_int >>>> 3\n");
2123                         else
2124                                 IFX_MEI_DMSG("got int = %d\n", got_int);
2125                         got_int = 0;
2126                         //schedule();
2127                         DSL_ENABLE_IRQ (pDev->nIrq[IFX_DFEIR]);
2128                 }
2129                 //mbox_read(&rd_mbox[0],6);
2130                 MEI_WAIT (100);
2131         }
2132         return 0;
2133 }
2134
2135 static DSL_DEV_MeiError_t
2136 DFE_Loopback_Test (void)
2137 {
2138         int i = 0;
2139         u32 arc_debug_data = 0, temp;
2140         DSL_DEV_Device_t *pDev = &dsl_devices[0];
2141         uint32_t wr_mbox[10];
2142
2143         IFX_MEI_ResetARC (pDev);
2144         // start the clock
2145         arc_debug_data = ACL_CLK_MODE_ENABLE;
2146         IFX_MEI_DebugWrite (pDev, CRI_CCR0, &arc_debug_data, 1);
2147
2148 #if defined( DFE_PING_TEST )|| defined( DFE_ATM_LOOPBACK)
2149         // WriteARCreg(AUX_XMEM_LTEST,0);
2150         IFX_MEI_ControlModeSet (pDev, MEI_MASTER_MODE);
2151 #define AUX_XMEM_LTEST 0x128
2152         _IFX_MEI_DBGLongWordWrite (pDev, MEI_DEBUG_DEC_AUX_MASK,  AUX_XMEM_LTEST, 0);
2153         IFX_MEI_ControlModeSet (pDev, JTAG_MASTER_MODE);
2154
2155         // WriteARCreg(AUX_XDMA_GAP,0);
2156         IFX_MEI_ControlModeSet (pDev, MEI_MASTER_MODE);
2157 #define AUX_XDMA_GAP 0x114
2158         _IFX_MEI_DBGLongWordWrite (pDev, MEI_DEBUG_DEC_AUX_MASK, AUX_XDMA_GAP, 0);
2159         IFX_MEI_ControlModeSet (pDev, JTAG_MASTER_MODE);
2160
2161         IFX_MEI_ControlModeSet (pDev, MEI_MASTER_MODE);
2162         temp = 0;
2163         _IFX_MEI_DBGLongWordWrite (pDev, MEI_DEBUG_DEC_AUX_MASK,
2164                 (u32) ME_XDATA_BASE_SH +  LTQ_MEI_BASE_ADDR, temp);
2165         IFX_MEI_ControlModeSet (pDev, JTAG_MASTER_MODE);
2166
2167         i = IFX_MEI_DFEMemoryAlloc (pDev, SDRAM_SEGMENT_SIZE * 16);
2168         if (i >= 0) {
2169                 int idx;
2170
2171                 for (idx = 0; idx < i; idx++) {
2172                         DSL_DEV_PRIVATE(pDev)->adsl_mem_info[idx].type = FREE_RELOAD;
2173                         IFX_MEI_WRITE_REGISTER_L ((((uint32_t) DSL_DEV_PRIVATE(pDev)->adsl_mem_info[idx].address) & 0x0fffffff),
2174                                                         LTQ_MEI_BASE_ADDR + ME_XMEM_BAR_BASE  + idx * 4);
2175                         IFX_MEI_DMSG("bar%d(%X)=%X\n", idx,
2176                                 LTQ_MEI_BASE_ADDR + ME_XMEM_BAR_BASE  +
2177                                 idx * 4, (((uint32_t)
2178                                            ((ifx_mei_device_private_t *)
2179                                             pDev->pPriv)->adsl_mem_info[idx].
2180                                            address) & 0x0fffffff));
2181                         memset ((u8 *) DSL_DEV_PRIVATE(pDev)->adsl_mem_info[idx].address, 0, SDRAM_SEGMENT_SIZE);
2182                 }
2183
2184                 IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_XDATA_BASE_SH,
2185                                            ((unsigned long) DSL_DEV_PRIVATE(pDev)->adsl_mem_info[XDATA_REGISTER].address) & 0x0FFFFFFF);
2186         }
2187         else {
2188                 IFX_MEI_EMSG ("cannot load image: no memory\n");
2189                 return DSL_DEV_MEI_ERR_FAILURE;
2190         }
2191         //WriteARCreg(AUX_IC_CTRL,2);
2192         IFX_MEI_DMSG("Setting MEI_MASTER_MODE..\n");
2193         IFX_MEI_ControlModeSet (pDev, MEI_MASTER_MODE);
2194 #define AUX_IC_CTRL 0x11
2195         _IFX_MEI_DBGLongWordWrite (pDev, MEI_DEBUG_DEC_AUX_MASK,
2196                                          AUX_IC_CTRL, 2);
2197         IFX_MEI_DMSG("Setting JTAG_MASTER_MODE..\n");
2198         IFX_MEI_ControlModeSet (pDev, JTAG_MASTER_MODE);
2199
2200         IFX_MEI_DMSG("Halting ARC...\n");
2201         IFX_MEI_HaltArc (&dsl_devices[0]);
2202
2203 #ifdef DFE_PING_TEST
2204
2205         IFX_MEI_DMSG("ping test image size=%d\n", sizeof (arc_ahb_access_code));
2206         memcpy ((u8 *) (DSL_DEV_PRIVATE(pDev)->
2207                         adsl_mem_info[0].address + 0x1004),
2208                 &arc_ahb_access_code[0], sizeof (arc_ahb_access_code));
2209         load_jump_table (0x80000 + 0x1004);
2210
2211 #endif //DFE_PING_TEST
2212
2213         IFX_MEI_DMSG("ARC ping test code download complete\n");
2214 #endif //defined( DFE_PING_TEST )|| defined( DFE_ATM_LOOPBACK)
2215 #ifdef DFE_MEM_TEST
2216         IFX_MEI_LongWordWriteOffset (&dsl_devices[0], (u32) ME_ARC2ME_MASK, MSGAV_EN);
2217
2218         arc_code_page_download (1537, &code_array[0]);
2219         IFX_MEI_DMSG("ARC mem test code download complete\n");
2220 #endif //DFE_MEM_TEST
2221 #ifdef DFE_ATM_LOOPBACK
2222         arc_debug_data = 0xf;
2223         arc_code_page_download (sizeof(code_array) / sizeof(*code_array), &code_array[0]);
2224         wr_mbox[0] = 0;     //TIMER_DELAY   - org: 1024
2225         wr_mbox[1] = 0;         //TXFB_START0
2226         wr_mbox[2] = 0x7f;      //TXFB_END0     - org: 49
2227         wr_mbox[3] = 0x80;      //TXFB_START1   - org: 80
2228         wr_mbox[4] = 0xff;      //TXFB_END1     - org: 109
2229         wr_mbox[5] = 0x100;     //RXFB_START0   - org: 0
2230         wr_mbox[6] = 0x17f;     //RXFB_END0     - org: 49
2231         wr_mbox[7] = 0x180;     //RXFB_START1   - org: 256
2232         wr_mbox[8] = 0x1ff;     //RXFB_END1     - org: 315
2233         WriteMbox (&wr_mbox[0], 9);
2234         // Start Iridia IT_AMODE (in dmp access) why is it required?
2235         IFX_MEI_DebugWrite (&dsl_devices[0], 0x32010, &arc_debug_data, 1);
2236 #endif //DFE_ATM_LOOPBACK
2237         IFX_MEI_IRQEnable (pDev);
2238         IFX_MEI_DMSG("run ARC...\n");
2239         IFX_MEI_RunArc (&dsl_devices[0]);
2240
2241 #ifdef DFE_PING_TEST
2242         arc_ping_testing (pDev);
2243 #endif //DFE_PING_TEST
2244 #ifdef DFE_MEM_TEST
2245         wait_mem_test_result ();
2246 #endif //DFE_MEM_TEST
2247
2248         IFX_MEI_DFEMemoryFree (pDev, FREE_ALL);
2249         return DSL_DEV_MEI_ERR_SUCCESS;
2250 }
2251
2252 #endif //CONFIG_AMAZON_S_MEI_FW_LOOPBACK
2253
2254 static int
2255 IFX_MEI_InitDevNode (int num)
2256 {
2257         if (num == 0) {
2258                 if ((dev_major = register_chrdev (dev_major, IFX_MEI_DEVNAME, &bsp_mei_operations)) < 0) {
2259                         IFX_MEI_EMSG ("register_chrdev(%d %s) failed!\n", dev_major, IFX_MEI_DEVNAME);
2260                         return -ENODEV;
2261                 }
2262         }
2263         return 0;
2264 }
2265
2266 static int
2267 IFX_MEI_CleanUpDevNode (int num)
2268 {
2269         if (num == 0)
2270                 unregister_chrdev (dev_major, MEI_DIRNAME);
2271         return 0;
2272 }
2273
2274 static int
2275 IFX_MEI_InitDevice (int num)
2276 {
2277         DSL_DEV_Device_t *pDev;
2278         u32 temp;
2279         pDev = &dsl_devices[num];
2280         if (pDev == NULL)
2281                 return -ENOMEM;
2282         pDev->pPriv = &sDanube_Mei_Private[num];
2283         memset (pDev->pPriv, 0, sizeof (ifx_mei_device_private_t));
2284
2285         memset (&DSL_DEV_PRIVATE(pDev)->
2286                 adsl_mem_info[0], 0,
2287                 sizeof (smmu_mem_info_t) * MAX_BAR_REGISTERS);
2288
2289         if (num == 0) {
2290                 pDev->nIrq[IFX_DFEIR]      = LTQ_MEI_INT;
2291                 pDev->nIrq[IFX_DYING_GASP] = LTQ_MEI_DYING_GASP_INT;
2292                 pDev->base_address = KSEG1 + LTQ_MEI_BASE_ADDR;
2293
2294                 /* Power up MEI */
2295 #ifdef CONFIG_LANTIQ_AMAZON_SE
2296                 *LTQ_PMU_PWDCR &= ~(1 << 9);  // enable dsl
2297                 *LTQ_PMU_PWDCR &= ~(1 << 15); // enable AHB base
2298 #else
2299                 temp = ltq_r32(LTQ_PMU_PWDCR);
2300                 temp &= 0xffff7dbe;
2301                 ltq_w32(temp, LTQ_PMU_PWDCR);
2302 #endif
2303         }
2304         pDev->nInUse = 0;
2305         DSL_DEV_PRIVATE(pDev)->modem_ready = 0;
2306         DSL_DEV_PRIVATE(pDev)->arcmsgav = 0;
2307
2308         MEI_INIT_WAKELIST ("arcq", DSL_DEV_PRIVATE(pDev)->wait_queue_arcmsgav); // for ARCMSGAV
2309         MEI_INIT_WAKELIST ("arcr", DSL_DEV_PRIVATE(pDev)->wait_queue_modemready);       // for arc modem ready
2310
2311         MEI_MUTEX_INIT (DSL_DEV_PRIVATE(pDev)->mei_cmv_sema, 1);        // semaphore initialization, mutex
2312 #if 0
2313         MEI_MASK_AND_ACK_IRQ (pDev->nIrq[IFX_DFEIR]);
2314         MEI_MASK_AND_ACK_IRQ (pDev->nIrq[IFX_DYING_GASP]);
2315 #endif
2316         if (request_irq (pDev->nIrq[IFX_DFEIR], IFX_MEI_IrqHandle, 0, "DFEIR", pDev) != 0) {
2317                 IFX_MEI_EMSG ("request_irq %d failed!\n", pDev->nIrq[IFX_DFEIR]);
2318                 return -1;
2319         }
2320         /*if (request_irq (pDev->nIrq[IFX_DYING_GASP], IFX_MEI_Dying_Gasp_IrqHandle, 0, "DYING_GASP", pDev) != 0) {
2321                 IFX_MEI_EMSG ("request_irq %d failed!\n", pDev->nIrq[IFX_DYING_GASP]);
2322                 return -1;
2323         }*/
2324 //      IFX_MEI_DMSG("Device %d initialized. IER %#x\n", num, bsp_get_irq_ier(pDev->nIrq[IFX_DYING_GASP]));
2325         return 0;
2326 }
2327
2328 static int
2329 IFX_MEI_ExitDevice (int num)
2330 {
2331         DSL_DEV_Device_t *pDev;
2332         pDev = &dsl_devices[num];
2333
2334         if (pDev == NULL)
2335                 return -EIO;
2336
2337         disable_irq (pDev->nIrq[IFX_DFEIR]);
2338         disable_irq (pDev->nIrq[IFX_DYING_GASP]);
2339
2340         free_irq(pDev->nIrq[IFX_DFEIR], pDev);
2341         free_irq(pDev->nIrq[IFX_DYING_GASP], pDev);
2342
2343         return 0;
2344 }
2345
2346 static DSL_DEV_Device_t *
2347 IFX_BSP_HandleGet (int maj, int num)
2348 {
2349         if (num > BSP_MAX_DEVICES)
2350                 return NULL;
2351         return &dsl_devices[num];
2352 }
2353
2354 DSL_DEV_Device_t *
2355 DSL_BSP_DriverHandleGet (int maj, int num)
2356 {
2357         DSL_DEV_Device_t *pDev;
2358
2359         if (num > BSP_MAX_DEVICES)
2360                 return NULL;
2361
2362         pDev = &dsl_devices[num];
2363         if (!try_module_get(pDev->owner))
2364                 return NULL;
2365
2366         pDev->nInUse++;
2367         return pDev;
2368 }
2369
2370 int
2371 DSL_BSP_DriverHandleDelete (DSL_DEV_Device_t * nHandle)
2372 {
2373         DSL_DEV_Device_t *pDev = (DSL_DEV_Device_t *) nHandle;
2374         if (pDev->nInUse)
2375                 pDev->nInUse--;
2376         module_put(pDev->owner);
2377         return 0;
2378 }
2379
2380 static int
2381 IFX_MEI_Open (DSL_DRV_inode_t * ino, DSL_DRV_file_t * fil)
2382 {
2383         int maj = MAJOR (ino->i_rdev);
2384         int num = MINOR (ino->i_rdev);
2385
2386         DSL_DEV_Device_t *pDev = NULL;
2387         if ((pDev = DSL_BSP_DriverHandleGet (maj, num)) == NULL) {
2388                 IFX_MEI_EMSG("open(%d:%d) fail!\n", maj, num);
2389                 return -EIO;
2390         }
2391         fil->private_data = pDev;
2392         return 0;
2393 }
2394
2395 static int
2396 IFX_MEI_Release (DSL_DRV_inode_t * ino, DSL_DRV_file_t * fil)
2397 {
2398         //int maj = MAJOR(ino->i_rdev);
2399         int num = MINOR (ino->i_rdev);
2400         DSL_DEV_Device_t *pDev;
2401
2402         pDev = &dsl_devices[num];
2403         if (pDev == NULL)
2404                 return -EIO;
2405         DSL_BSP_DriverHandleDelete (pDev);
2406         return 0;
2407 }
2408
2409 /**
2410  * Callback function for linux userspace program writing
2411  */
2412 static ssize_t
2413 IFX_MEI_Write (DSL_DRV_file_t * filp, const char *buf, size_t size, loff_t * loff)
2414 {
2415         DSL_DEV_MeiError_t mei_error = DSL_DEV_MEI_ERR_FAILURE;
2416         long offset = 0;
2417         DSL_DEV_Device_t *pDev = (DSL_DEV_Device_t *) filp->private_data;
2418
2419         if (pDev == NULL)
2420                 return -EIO;
2421
2422         mei_error =
2423                 DSL_BSP_FWDownload (pDev, buf, size, (long *) loff,  &offset);
2424
2425         if (mei_error == DSL_DEV_MEI_ERR_FAILURE)
2426                 return -EIO;
2427         return (ssize_t) offset;
2428 }
2429
2430 /**
2431  * Callback function for linux userspace program ioctling
2432  */
2433 static int
2434 IFX_MEI_IoctlCopyFrom (int from_kernel, char *dest, char *from, int size)
2435 {
2436         int ret = 0;
2437
2438         if (!from_kernel)
2439                 ret = copy_from_user ((char *) dest, (char *) from, size);
2440         else
2441                 ret = (int)memcpy ((char *) dest, (char *) from, size);
2442         return ret;
2443 }
2444
2445 static int
2446 IFX_MEI_IoctlCopyTo (int from_kernel, char *dest, char *from, int size)
2447 {
2448         int ret = 0;
2449
2450         if (!from_kernel)
2451                 ret = copy_to_user ((char *) dest, (char *) from, size);
2452         else
2453                 ret = (int)memcpy ((char *) dest, (char *) from, size);
2454         return ret;
2455 }
2456
2457 static int
2458 IFX_MEI_Ioctls (DSL_DEV_Device_t * pDev, int from_kernel, unsigned int command, unsigned long lon)
2459 {
2460         int i = 0;
2461         int meierr = DSL_DEV_MEI_ERR_SUCCESS;
2462         u32 base_address = LTQ_MEI_BASE_ADDR;
2463         DSL_DEV_WinHost_Message_t winhost_msg, m;
2464         DSL_DEV_MeiDebug_t debugrdwr;
2465         DSL_DEV_MeiReg_t regrdwr;
2466
2467         switch (command) {
2468
2469         case DSL_FIO_BSP_CMV_WINHOST:
2470                 IFX_MEI_IoctlCopyFrom (from_kernel, (char *) winhost_msg.msg.TxMessage,
2471                                              (char *) lon, MSG_LENGTH * 2);
2472
2473                 if ((meierr = DSL_BSP_SendCMV (pDev, winhost_msg.msg.TxMessage, YES_REPLY,
2474                                            winhost_msg.msg.RxMessage)) != DSL_DEV_MEI_ERR_SUCCESS) {
2475                         IFX_MEI_EMSG ("WINHOST CMV fail :TxMessage:%X %X %X %X, RxMessage:%X %X %X %X %X\n",
2476                                  winhost_msg.msg.TxMessage[0], winhost_msg.msg.TxMessage[1], winhost_msg.msg.TxMessage[2], winhost_msg.msg.TxMessage[3],
2477                                  winhost_msg.msg.RxMessage[0], winhost_msg.msg.RxMessage[1], winhost_msg.msg.RxMessage[2], winhost_msg.msg.RxMessage[3],
2478                                  winhost_msg.msg.RxMessage[4]);
2479                         meierr = DSL_DEV_MEI_ERR_FAILURE;
2480                 }
2481                 else {
2482                         IFX_MEI_IoctlCopyTo (from_kernel, (char *) lon,
2483                                                    (char *) winhost_msg.msg.RxMessage,
2484                                                    MSG_LENGTH * 2);
2485                 }
2486                 break;
2487
2488         case DSL_FIO_BSP_CMV_READ:
2489                 IFX_MEI_IoctlCopyFrom (from_kernel, (char *) (&regrdwr),
2490                                              (char *) lon, sizeof (DSL_DEV_MeiReg_t));
2491
2492                 IFX_MEI_LongWordRead ((u32) regrdwr.iAddress,
2493                                             (u32 *) & (regrdwr.iData));
2494
2495                 IFX_MEI_IoctlCopyTo (from_kernel, (char *) lon,
2496                                            (char *) (&regrdwr),
2497                                            sizeof (DSL_DEV_MeiReg_t));
2498
2499                 break;
2500
2501         case DSL_FIO_BSP_CMV_WRITE:
2502                 IFX_MEI_IoctlCopyFrom (from_kernel, (char *) (&regrdwr),
2503                                              (char *) lon, sizeof (DSL_DEV_MeiReg_t));
2504
2505                 IFX_MEI_LongWordWrite ((u32) regrdwr.iAddress,
2506                                              regrdwr.iData);
2507                 break;
2508
2509         case DSL_FIO_BSP_GET_BASE_ADDRESS:
2510                 IFX_MEI_IoctlCopyTo (from_kernel, (char *) lon,
2511                                            (char *) (&base_address),
2512                                            sizeof (base_address));
2513                 break;
2514
2515         case DSL_FIO_BSP_IS_MODEM_READY:
2516                 i = IFX_MEI_IsModemReady (pDev);
2517                 IFX_MEI_IoctlCopyTo (from_kernel, (char *) lon,
2518                                            (char *) (&i), sizeof (int));
2519                 meierr = DSL_DEV_MEI_ERR_SUCCESS;
2520                 break;
2521         case DSL_FIO_BSP_RESET:
2522         case DSL_FIO_BSP_REBOOT:
2523                 meierr = IFX_MEI_CpuModeSet (pDev, DSL_CPU_RESET);
2524                 meierr = IFX_MEI_CpuModeSet (pDev, DSL_CPU_HALT);
2525                 break;
2526
2527         case DSL_FIO_BSP_HALT:
2528                 meierr = IFX_MEI_CpuModeSet (pDev, DSL_CPU_HALT);
2529                 break;
2530
2531         case DSL_FIO_BSP_RUN:
2532                 meierr = IFX_MEI_CpuModeSet (pDev, DSL_CPU_RUN);
2533                 break;
2534         case DSL_FIO_BSP_BOOTDOWNLOAD:
2535                 meierr = IFX_MEI_DownloadBootCode (pDev);
2536                 break;
2537         case DSL_FIO_BSP_JTAG_ENABLE:
2538                 meierr = IFX_MEI_ArcJtagEnable (pDev, 1);
2539                 break;
2540
2541         case DSL_FIO_BSP_REMOTE:
2542                 IFX_MEI_IoctlCopyFrom (from_kernel, (char *) (&i),
2543                                              (char *) lon, sizeof (int));
2544
2545                 meierr = IFX_MEI_AdslMailboxIRQEnable (pDev, i);
2546                 break;
2547
2548         case DSL_FIO_BSP_DSL_START:
2549                 IFX_MEI_DMSG("DSL_FIO_BSP_DSL_START\n");
2550                 if ((meierr = IFX_MEI_RunAdslModem (pDev)) != DSL_DEV_MEI_ERR_SUCCESS) {
2551                         IFX_MEI_EMSG ("IFX_MEI_RunAdslModem() error...");
2552                         meierr = DSL_DEV_MEI_ERR_FAILURE;
2553                 }
2554                 break;
2555
2556         case DSL_FIO_BSP_DEBUG_READ:
2557         case DSL_FIO_BSP_DEBUG_WRITE:
2558                 IFX_MEI_IoctlCopyFrom (from_kernel,
2559                                              (char *) (&debugrdwr),
2560                                              (char *) lon,
2561                                              sizeof (debugrdwr));
2562
2563                 if (command == DSL_FIO_BSP_DEBUG_READ)
2564                         meierr = DSL_BSP_MemoryDebugAccess (pDev,
2565                                                                  DSL_BSP_MEMORY_READ,
2566                                                                  debugrdwr.
2567                                                                  iAddress,
2568                                                                  debugrdwr.
2569                                                                  buffer,
2570                                                                  debugrdwr.
2571                                                                  iCount);
2572                 else
2573                         meierr = DSL_BSP_MemoryDebugAccess (pDev,
2574                                                                  DSL_BSP_MEMORY_WRITE,
2575                                                                  debugrdwr.
2576                                                                  iAddress,
2577                                                                  debugrdwr.
2578                                                                  buffer,
2579                                                                  debugrdwr.
2580                                                                  iCount);
2581
2582                 IFX_MEI_IoctlCopyTo (from_kernel, (char *) lon, (char *) (&debugrdwr), sizeof (debugrdwr));
2583                 break;
2584         case DSL_FIO_BSP_GET_VERSION:
2585                 IFX_MEI_IoctlCopyTo (from_kernel, (char *) lon, (char *) (&bsp_mei_version), sizeof (DSL_DEV_Version_t));
2586                 break;
2587
2588 #define LTQ_MPS_CHIPID_VERSION_GET(value)  (((value) >> 28) & ((1 << 4) - 1))
2589         case DSL_FIO_BSP_GET_CHIP_INFO:
2590                 bsp_chip_info.major = 1;
2591                 bsp_chip_info.minor = LTQ_MPS_CHIPID_VERSION_GET(*LTQ_MPS_CHIPID);
2592                 IFX_MEI_IoctlCopyTo (from_kernel, (char *) lon, (char *) (&bsp_chip_info), sizeof (DSL_DEV_HwVersion_t));
2593                 meierr = DSL_DEV_MEI_ERR_SUCCESS;
2594                 break;
2595
2596         case DSL_FIO_BSP_FREE_RESOURCE:
2597                 makeCMV (H2D_CMV_READ, DSL_CMV_GROUP_STAT, 4, 0, 1, NULL, m.msg.TxMessage);
2598                 if (DSL_BSP_SendCMV (pDev, m.msg.TxMessage, YES_REPLY, m.msg.RxMessage) != DSL_DEV_MEI_ERR_SUCCESS) {
2599                         meierr = DSL_DEV_MEI_ERR_FAILURE;
2600                         return -EIO;
2601                 }
2602                 IFX_MEI_DMSG("RxMessage[4] = %#x\n", m.msg.RxMessage[4]);
2603                 if (!(m.msg.RxMessage[4] & DSL_DEV_STAT_CODESWAP_COMPLETE)) {
2604                         meierr = DSL_DEV_MEI_ERR_FAILURE;
2605                         return -EAGAIN;
2606                 }
2607                 IFX_MEI_DMSG("Freeing all memories marked FREE_SHOWTIME\n");
2608                 IFX_MEI_DFEMemoryFree (pDev, FREE_SHOWTIME);
2609                 meierr = DSL_DEV_MEI_ERR_SUCCESS;
2610                 break;
2611 #ifdef CONFIG_IFXMIPS_AMAZON_SE
2612         case DSL_FIO_ARC_MUX_TEST:
2613                 AMAZON_SE_MEI_ARC_MUX_Test();
2614                 break;
2615 #endif
2616         default:
2617 //              IFX_MEI_EMSG("Invalid IOCTL command: %d\n");
2618                 break;
2619         }
2620         return meierr;
2621 }
2622
2623 #ifdef CONFIG_IFXMIPS_AMAZON_SE
2624 void AMAZON_SE_MEI_ARC_MUX_Test(void)
2625 {
2626         u32 *p, i;
2627         *LTQ_RCU_RST |= LTQ_RCU_RST_REQ_MUX_ARC;
2628
2629         p = (u32*)(DFE_LDST_BASE_ADDR + IRAM0_BASE);
2630         IFX_MEI_EMSG("Writing to IRAM0(%p)...\n", p);
2631         for (i = 0; i < IRAM0_SIZE/sizeof(u32); i++, p++) {
2632                 *p = 0xdeadbeef;
2633                 if (*p != 0xdeadbeef)
2634                         IFX_MEI_EMSG("%p: %#x\n", p, *p);
2635         }
2636
2637         p = (u32*)(DFE_LDST_BASE_ADDR + IRAM1_BASE);
2638         IFX_MEI_EMSG("Writing to IRAM1(%p)...\n", p);
2639         for (i = 0; i < IRAM1_SIZE/sizeof(u32); i++, p++) {
2640                 *p = 0xdeadbeef;
2641                 if (*p != 0xdeadbeef)
2642                         IFX_MEI_EMSG("%p: %#x\n", p, *p);
2643         }
2644
2645         p = (u32*)(DFE_LDST_BASE_ADDR + BRAM_BASE);
2646         IFX_MEI_EMSG("Writing to BRAM(%p)...\n", p);
2647         for (i = 0; i < BRAM_SIZE/sizeof(u32); i++, p++) {
2648                 *p = 0xdeadbeef;
2649                 if (*p != 0xdeadbeef)
2650                         IFX_MEI_EMSG("%p: %#x\n", p, *p);
2651         }
2652
2653         p = (u32*)(DFE_LDST_BASE_ADDR + XRAM_BASE);
2654         IFX_MEI_EMSG("Writing to XRAM(%p)...\n", p);
2655         for (i = 0; i < XRAM_SIZE/sizeof(u32); i++, p++) {
2656                 *p = 0xdeadbeef;
2657                 if (*p != 0xdeadbeef)
2658                         IFX_MEI_EMSG("%p: %#x\n", p, *p);
2659         }
2660
2661         p = (u32*)(DFE_LDST_BASE_ADDR + YRAM_BASE);
2662         IFX_MEI_EMSG("Writing to YRAM(%p)...\n", p);
2663         for (i = 0; i < YRAM_SIZE/sizeof(u32); i++, p++) {
2664                 *p = 0xdeadbeef;
2665                 if (*p != 0xdeadbeef)
2666                         IFX_MEI_EMSG("%p: %#x\n", p, *p);
2667         }
2668
2669         p = (u32*)(DFE_LDST_BASE_ADDR + EXT_MEM_BASE);
2670         IFX_MEI_EMSG("Writing to EXT_MEM(%p)...\n", p);
2671         for (i = 0; i < EXT_MEM_SIZE/sizeof(u32); i++, p++) {
2672                 *p = 0xdeadbeef;
2673                 if (*p != 0xdeadbeef)
2674                         IFX_MEI_EMSG("%p: %#x\n", p, *p);
2675         }
2676         *LTQ_RCU_RST &= ~LTQ_RCU_RST_REQ_MUX_ARC;
2677 }
2678 #endif
2679 int
2680 DSL_BSP_KernelIoctls (DSL_DEV_Device_t * pDev, unsigned int command,
2681                            unsigned long lon)
2682 {
2683         int error = 0;
2684
2685         error = IFX_MEI_Ioctls (pDev, 1, command, lon);
2686         return error;
2687 }
2688
2689 #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,36))
2690 static int
2691 IFX_MEI_UserIoctls (DSL_DRV_inode_t * ino, DSL_DRV_file_t * fil,
2692                           unsigned int command, unsigned long lon)
2693 #else
2694 static int
2695 IFX_MEI_UserIoctls (DSL_DRV_file_t * fil,
2696                           unsigned int command, unsigned long lon)
2697 #endif
2698 {
2699         int error = 0;
2700 #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,36))
2701         int maj = MAJOR (ino->i_rdev);
2702         int num = MINOR (ino->i_rdev);
2703 #endif
2704         DSL_DEV_Device_t *pDev;
2705
2706 #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,36))
2707         pDev = IFX_BSP_HandleGet (maj, num);
2708 #else
2709         pDev = IFX_BSP_HandleGet (0, 0);
2710 #endif
2711         if (pDev == NULL)
2712                 return -EIO;
2713
2714         error = IFX_MEI_Ioctls (pDev, 0, command, lon);
2715         return error;
2716 }
2717
2718 #ifdef CONFIG_PROC_FS
2719 /*
2720  * Register a callback function for linux proc filesystem
2721  */
2722 static int
2723 IFX_MEI_InitProcFS (int num)
2724 {
2725         struct proc_dir_entry *entry;
2726         int i ;
2727         DSL_DEV_Device_t *pDev;
2728         reg_entry_t regs_temp[PROC_ITEMS] = {
2729                 /* flag, name,      description } */
2730                 {NULL, "arcmsgav", "arc to mei message ", 0},
2731                 {NULL, "cmv_reply", "cmv needs reply", 0},
2732                 {NULL, "cmv_waiting", "waiting for cmv reply from arc", 0},
2733                 {NULL, "modem_ready_cnt", "ARC to MEI indicator count", 0},
2734                 {NULL, "cmv_count", "MEI to ARC CMVs", 0},
2735                 {NULL, "reply_count", "ARC to MEI Reply", 0},
2736                 {NULL, "Recent_indicator", "most recent indicator", 0},
2737                 {NULL, "fw_version", "Firmware Version", 0},
2738                 {NULL, "fw_date", "Firmware Date", 0},
2739                 {NULL, "meminfo", "Memory Allocation Information", 0},
2740                 {NULL, "version", "MEI version information", 0},
2741         };
2742
2743         pDev = &dsl_devices[num];
2744         if (pDev == NULL)
2745                 return -ENOMEM;
2746
2747         regs_temp[0].flag = &(DSL_DEV_PRIVATE(pDev)->arcmsgav);
2748         regs_temp[1].flag = &(DSL_DEV_PRIVATE(pDev)->cmv_reply);
2749         regs_temp[2].flag = &(DSL_DEV_PRIVATE(pDev)->cmv_waiting);
2750         regs_temp[3].flag = &(DSL_DEV_PRIVATE(pDev)->modem_ready_cnt);
2751         regs_temp[4].flag = &(DSL_DEV_PRIVATE(pDev)->cmv_count);
2752         regs_temp[5].flag = &(DSL_DEV_PRIVATE(pDev)->reply_count);
2753         regs_temp[6].flag = (int *) &(DSL_DEV_PRIVATE(pDev)->Recent_indicator);
2754
2755         memcpy ((char *) regs[num], (char *) regs_temp, sizeof (regs_temp));
2756         // procfs
2757         meidir = proc_mkdir (MEI_DIRNAME, NULL);
2758         if (meidir == NULL) {
2759                 IFX_MEI_EMSG ("Failed to create /proc/%s\n",  MEI_DIRNAME);
2760                 return (-ENOMEM);
2761         }
2762
2763         for (i = 0; i < NUM_OF_REG_ENTRY; i++) {
2764                 entry = create_proc_entry (regs[num][i].name,
2765                                            S_IWUSR | S_IRUSR | S_IRGRP |
2766                                            S_IROTH, meidir);
2767                 if (entry) {
2768                         regs[num][i].low_ino = entry->low_ino;
2769                         entry->proc_fops = &IFX_MEI_ProcOperations;
2770                 }
2771                 else {
2772                         IFX_MEI_EMSG ("Failed to create /proc/%s/%s\n", MEI_DIRNAME, regs[num][i].name);
2773                         return (-ENOMEM);
2774                 }
2775         }
2776         return 0;
2777 }
2778
2779 /*
2780  * Reading function for linux proc filesystem
2781  */
2782 static int
2783 IFX_MEI_ProcRead (struct file *file, char *buf, size_t nbytes, loff_t * ppos)
2784 {
2785         int i_ino = (file->f_dentry->d_inode)->i_ino;
2786         char *p = buf;
2787         int i;
2788         int num;
2789         reg_entry_t *entry = NULL;
2790         DSL_DEV_Device_t *pDev = NULL;
2791         DSL_DEV_WinHost_Message_t m;
2792
2793         for (num = 0; num < BSP_MAX_DEVICES; num++) {
2794                 for (i = 0; i < NUM_OF_REG_ENTRY; i++) {
2795                         if (regs[num][i].low_ino == (unsigned short)i_ino) {
2796                                 entry = &regs[num][i];
2797                                 pDev = &dsl_devices[num];
2798                                 break;
2799                         }
2800                 }
2801         }
2802         if (entry == NULL)
2803                 return -EINVAL;
2804         else if (strcmp(entry->name, "meminfo") == 0) {
2805                 if (*ppos > 0)  /* Assume reading completed in previous read */
2806                         return 0;
2807                 p += sprintf (p, "No           Address     Size\n");
2808                 for (i = 0; i < MAX_BAR_REGISTERS; i++) {
2809                         p += sprintf (p, "BAR[%02d] Addr:0x%08X Size:%lu\n",
2810                                           i, (u32) DSL_DEV_PRIVATE(pDev)->adsl_mem_info[i].address,
2811                                           DSL_DEV_PRIVATE(pDev)-> adsl_mem_info[i].size);
2812                         //printk( "BAR[%02d] Addr:0x%08X Size:%d\n",i,adsl_mem_info[i].address,adsl_mem_info[i].size);
2813                 }
2814                 *ppos += (p - buf);
2815         } else if (strcmp(entry->name, "fw_version") == 0) {
2816                 if (*ppos > 0)  /* Assume reading completed in previous read */
2817                         return 0;
2818                 if (DSL_DEV_PRIVATE(pDev)->modem_ready_cnt < 1)
2819                         return -EAGAIN;
2820                 //major:bits 0-7
2821                 //minor:bits 8-15
2822                 makeCMV (H2D_CMV_READ, DSL_CMV_GROUP_INFO, 54, 0, 1, NULL, m.msg.TxMessage);
2823                 if (DSL_BSP_SendCMV (pDev, m.msg.TxMessage, YES_REPLY, m.msg.RxMessage) != DSL_DEV_MEI_ERR_SUCCESS)
2824                         return -EIO;
2825                 p += sprintf(p, "FW Version: %d.%d.", m.msg.RxMessage[4] & 0xFF, (m.msg.RxMessage[4] >> 8) & 0xFF);
2826                 //sub_version:bits 4-7
2827                 //int_version:bits 0-3
2828                 //spl_appl:bits 8-13
2829                 //rel_state:bits 14-15
2830                 makeCMV (H2D_CMV_READ, DSL_CMV_GROUP_INFO, 54, 1, 1, NULL, m.msg.TxMessage);
2831                 if (DSL_BSP_SendCMV (pDev, m.msg.TxMessage, YES_REPLY, m.msg.RxMessage) != DSL_DEV_MEI_ERR_SUCCESS)
2832                         return -EIO;
2833                 p += sprintf(p, "%d.%d.%d.%d\n",
2834                         (m.msg.RxMessage[4] >> 4) & 0xF, m.msg.RxMessage[4] & 0xF,
2835                         (m.msg.RxMessage[4] >> 14) & 3, (m.msg.RxMessage[4] >> 8) & 0x3F);
2836                 *ppos += (p - buf);
2837         } else if (strcmp(entry->name, "fw_date") == 0) {
2838                 if (*ppos > 0)  /* Assume reading completed in previous read */
2839                         return 0;
2840                 if (DSL_DEV_PRIVATE(pDev)->modem_ready_cnt < 1)
2841                         return -EAGAIN;
2842
2843                 makeCMV (H2D_CMV_READ, DSL_CMV_GROUP_INFO, 55, 0, 1, NULL, m.msg.TxMessage);
2844                 if (DSL_BSP_SendCMV (pDev, m.msg.TxMessage, YES_REPLY, m.msg.RxMessage) != DSL_DEV_MEI_ERR_SUCCESS)
2845                         return -EIO;
2846                 /* Day/Month */
2847                 p += sprintf(p, "FW Date: %d.%d.", m.msg.RxMessage[4] & 0xFF, (m.msg.RxMessage[4] >> 8) & 0xFF);
2848
2849                 makeCMV (H2D_CMV_READ, DSL_CMV_GROUP_INFO, 55, 2, 1, NULL, m.msg.TxMessage);
2850                 if (DSL_BSP_SendCMV (pDev, m.msg.TxMessage, YES_REPLY, m.msg.RxMessage) != DSL_DEV_MEI_ERR_SUCCESS)
2851                         return -EIO;
2852                 /* Year */
2853                 p += sprintf(p, "%d ", m.msg.RxMessage[4]);
2854
2855                 makeCMV (H2D_CMV_READ, DSL_CMV_GROUP_INFO, 55, 1, 1, NULL, m.msg.TxMessage);
2856                 if (DSL_BSP_SendCMV (pDev, m.msg.TxMessage, YES_REPLY, m.msg.RxMessage) != DSL_DEV_MEI_ERR_SUCCESS)
2857                         return -EIO;
2858                 /* Hour:Minute */
2859                 p += sprintf(p, "%d:%d\n", (m.msg.RxMessage[4] >> 8) & 0xFF, m.msg.RxMessage[4] & 0xFF);
2860
2861                 *ppos += (p - buf);
2862         } else if (strcmp(entry->name, "version") == 0) {
2863                 if (*ppos > 0)  /* Assume reading completed in previous read */
2864                         return 0;
2865                 p += sprintf (p, "IFX MEI V%ld.%ld.%ld\n", bsp_mei_version.major, bsp_mei_version.minor, bsp_mei_version.revision);
2866
2867                 *ppos += (p - buf);
2868         } else if (entry->flag != (int *) DSL_DEV_PRIVATE(pDev)->Recent_indicator) {
2869                 if (*ppos > 0)  /* Assume reading completed in previous read */
2870                         return 0;       // indicates end of file
2871                 p += sprintf (p, "0x%08X\n\n", *(entry->flag));
2872                 *ppos += (p - buf);
2873                 if ((p - buf) > nbytes) /* Assume output can be read at one time */
2874                         return -EINVAL;
2875         } else {
2876                 if ((int) (*ppos) / ((int) 7) == 16)
2877                         return 0;       // indicate end of the message
2878                 p += sprintf (p, "0x%04X\n\n", *(((u16 *) (entry->flag)) + (int) (*ppos) / ((int) 7)));
2879                 *ppos += (p - buf);
2880         }
2881         return p -  buf;
2882 }
2883
2884 /*
2885  * Writing function for linux proc filesystem
2886  */
2887 static ssize_t
2888 IFX_MEI_ProcWrite (struct file *file, const char *buffer, size_t count, loff_t * ppos)
2889 {
2890         int i_ino = (file->f_dentry->d_inode)->i_ino;
2891         reg_entry_t *current_reg = NULL;
2892         int i = 0;
2893         int num = 0;
2894         unsigned long newRegValue = 0;
2895         char *endp = NULL;
2896         DSL_DEV_Device_t *pDev = NULL;
2897
2898         for (num = 0; num < BSP_MAX_DEVICES; num++) {
2899                 for (i = 0; i < NUM_OF_REG_ENTRY; i++) {
2900                         if (regs[num][i].low_ino == i_ino) {
2901                                 current_reg = &regs[num][i];
2902                                 pDev = &dsl_devices[num];
2903                                 break;
2904                         }
2905                 }
2906         }
2907         if ((current_reg == NULL)
2908             || (current_reg->flag ==
2909                 (int *) DSL_DEV_PRIVATE(pDev)->
2910                 Recent_indicator))
2911                 return -EINVAL;
2912
2913         newRegValue = simple_strtoul (buffer, &endp, 0);
2914         *(current_reg->flag) = (int) newRegValue;
2915         return (count + endp - buffer);
2916 }
2917 #endif //CONFIG_PROC_FS
2918
2919 static int adsl_dummy_ledcallback(void)
2920 {
2921     return 0;
2922 }
2923
2924 int ifx_mei_atm_led_blink(void)
2925 {
2926     return g_adsl_ledcallback();
2927 }
2928 EXPORT_SYMBOL(ifx_mei_atm_led_blink);
2929
2930 int ifx_mei_atm_showtime_check(int *is_showtime, struct port_cell_info *port_cell, void **xdata_addr)
2931 {
2932     int i;
2933
2934     if ( is_showtime ) {
2935         *is_showtime = g_tx_link_rate[0] == 0 && g_tx_link_rate[1] == 0 ? 0 : 1;
2936     }
2937
2938     if ( port_cell ) {
2939         for ( i = 0; i < port_cell->port_num && i < 2; i++ )
2940             port_cell->tx_link_rate[i] = g_tx_link_rate[i];
2941     }
2942
2943     if ( xdata_addr ) {
2944         if ( g_tx_link_rate[0] == 0 && g_tx_link_rate[1] == 0 )
2945             *xdata_addr = NULL;
2946         else
2947             *xdata_addr = g_xdata_addr;
2948     }
2949
2950     return 0;
2951 }
2952 EXPORT_SYMBOL(ifx_mei_atm_showtime_check);
2953
2954 /*
2955  * Writing function for linux proc filesystem
2956  */
2957 int __init
2958 IFX_MEI_ModuleInit (void)
2959 {
2960         int i = 0;
2961         static struct class *dsl_class;
2962
2963         pr_info("IFX MEI Version %ld.%02ld.%02ld", bsp_mei_version.major, bsp_mei_version.minor, bsp_mei_version.revision);
2964
2965         for (i = 0; i < BSP_MAX_DEVICES; i++) {
2966                 if (IFX_MEI_InitDevice (i) != 0) {
2967                         IFX_MEI_EMSG("Init device fail!\n");
2968                         return -EIO;
2969                 }
2970                 IFX_MEI_InitDevNode (i);
2971 #ifdef CONFIG_PROC_FS
2972                 IFX_MEI_InitProcFS (i);
2973 #endif
2974         }
2975                 for (i = 0; i <= DSL_BSP_CB_LAST ; i++)
2976                 dsl_bsp_event_callback[i].function = NULL;
2977
2978 #ifdef CONFIG_LTQ_MEI_FW_LOOPBACK
2979         IFX_MEI_DMSG("Start loopback test...\n");
2980         DFE_Loopback_Test ();
2981 #endif
2982         dsl_class = class_create(THIS_MODULE, "ifx_mei");
2983         device_create(dsl_class, NULL, MKDEV(MEI_MAJOR, 0), NULL, "ifx_mei");
2984         return 0;
2985 }
2986
2987 void __exit
2988 IFX_MEI_ModuleExit (void)
2989 {
2990         int i = 0;
2991         int num;
2992
2993         for (num = 0; num < BSP_MAX_DEVICES; num++) {
2994                 IFX_MEI_CleanUpDevNode (num);
2995 #ifdef CONFIG_PROC_FS
2996                 for (i = 0; i < NUM_OF_REG_ENTRY; i++) {
2997                         remove_proc_entry (regs[num][i].name, meidir);
2998                 }
2999 #endif
3000         }
3001
3002         remove_proc_entry (MEI_DIRNAME, NULL);
3003         for (i = 0; i < BSP_MAX_DEVICES; i++) {
3004                 for (i = 0; i < BSP_MAX_DEVICES; i++) {
3005                         IFX_MEI_ExitDevice (i);
3006                 }
3007         }
3008 }
3009
3010 /* export function for DSL Driver */
3011
3012 /* The functions of MEI_DriverHandleGet and MEI_DriverHandleDelete are
3013 something like open/close in kernel space , where the open could be used
3014 to register a callback for autonomous messages and returns a mei driver context pointer (comparable to the file descriptor in user space)
3015    The context will be required for the multi line chips future! */
3016
3017 EXPORT_SYMBOL (DSL_BSP_DriverHandleGet);
3018 EXPORT_SYMBOL (DSL_BSP_DriverHandleDelete);
3019
3020 EXPORT_SYMBOL (DSL_BSP_ATMLedCBRegister);
3021 EXPORT_SYMBOL (DSL_BSP_ATMLedCBUnregister);
3022 EXPORT_SYMBOL (DSL_BSP_KernelIoctls);
3023 EXPORT_SYMBOL (DSL_BSP_AdslLedInit);
3024 //EXPORT_SYMBOL (DSL_BSP_AdslLedSet);
3025 EXPORT_SYMBOL (DSL_BSP_FWDownload);
3026 EXPORT_SYMBOL (DSL_BSP_Showtime);
3027
3028 EXPORT_SYMBOL (DSL_BSP_MemoryDebugAccess);
3029 EXPORT_SYMBOL (DSL_BSP_SendCMV);
3030
3031 // provide a register/unregister function for DSL driver to register a event callback function
3032 EXPORT_SYMBOL (DSL_BSP_EventCBRegister);
3033 EXPORT_SYMBOL (DSL_BSP_EventCBUnregister);
3034
3035 module_init (IFX_MEI_ModuleInit);
3036 module_exit (IFX_MEI_ModuleExit);
3037
3038 MODULE_LICENSE("Dual BSD/GPL");