Linux Kernel  3.7.1
 All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros Groups Pages
smapi.c
Go to the documentation of this file.
1 /*
2 *
3 * smapi.c -- SMAPI interface routines
4 *
5 *
6 * Written By: Mike Sullivan IBM Corporation
7 *
8 * Copyright (C) 1999 IBM Corporation
9 *
10 * This program is free software; you can redistribute it and/or modify
11 * it under the terms of the GNU General Public License as published by
12 * the Free Software Foundation; either version 2 of the License, or
13 * (at your option) any later version.
14 *
15 * This program is distributed in the hope that it will be useful,
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 * GNU General Public License for more details.
19 *
20 * NO WARRANTY
21 * THE PROGRAM IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OR
22 * CONDITIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED INCLUDING, WITHOUT
23 * LIMITATION, ANY WARRANTIES OR CONDITIONS OF TITLE, NON-INFRINGEMENT,
24 * MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. Each Recipient is
25 * solely responsible for determining the appropriateness of using and
26 * distributing the Program and assumes all risks associated with its
27 * exercise of rights under this Agreement, including but not limited to
28 * the risks and costs of program errors, damage to or loss of data,
29 * programs or equipment, and unavailability or interruption of operations.
30 *
31 * DISCLAIMER OF LIABILITY
32 * NEITHER RECIPIENT NOR ANY CONTRIBUTORS SHALL HAVE ANY LIABILITY FOR ANY
33 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
34 * DAMAGES (INCLUDING WITHOUT LIMITATION LOST PROFITS), HOWEVER CAUSED AND
35 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR
36 * TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE
37 * USE OR DISTRIBUTION OF THE PROGRAM OR THE EXERCISE OF ANY RIGHTS GRANTED
38 * HEREUNDER, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGES
39 *
40 * You should have received a copy of the GNU General Public License
41 * along with this program; if not, write to the Free Software
42 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
43 *
44 *
45 * 10/23/2000 - Alpha Release
46 * First release to the public
47 */
48 
49 #include <linux/kernel.h>
50 #include <linux/mc146818rtc.h> /* CMOS defines */
51 #include "smapi.h"
52 #include "mwavedd.h"
53 
54 static unsigned short g_usSmapiPort = 0;
55 
56 
57 static int smapi_request(unsigned short inBX, unsigned short inCX,
58  unsigned short inDI, unsigned short inSI,
59  unsigned short *outAX, unsigned short *outBX,
60  unsigned short *outCX, unsigned short *outDX,
61  unsigned short *outDI, unsigned short *outSI)
62 {
63  unsigned short myoutAX = 2, *pmyoutAX = &myoutAX;
64  unsigned short myoutBX = 3, *pmyoutBX = &myoutBX;
65  unsigned short myoutCX = 4, *pmyoutCX = &myoutCX;
66  unsigned short myoutDX = 5, *pmyoutDX = &myoutDX;
67  unsigned short myoutDI = 6, *pmyoutDI = &myoutDI;
68  unsigned short myoutSI = 7, *pmyoutSI = &myoutSI;
69  unsigned short usSmapiOK = -EIO, *pusSmapiOK = &usSmapiOK;
70  unsigned int inBXCX = (inBX << 16) | inCX;
71  unsigned int inDISI = (inDI << 16) | inSI;
72  int retval = 0;
73 
74  PRINTK_5(TRACE_SMAPI, "inBX %x inCX %x inDI %x inSI %x\n",
75  inBX, inCX, inDI, inSI);
76 
77  __asm__ __volatile__("movw $0x5380,%%ax\n\t"
78  "movl %7,%%ebx\n\t"
79  "shrl $16, %%ebx\n\t"
80  "movw %7,%%cx\n\t"
81  "movl %8,%%edi\n\t"
82  "shrl $16,%%edi\n\t"
83  "movw %8,%%si\n\t"
84  "movw %9,%%dx\n\t"
85  "out %%al,%%dx\n\t"
86  "out %%al,$0x4F\n\t"
87  "cmpb $0x53,%%ah\n\t"
88  "je 2f\n\t"
89  "1:\n\t"
90  "orb %%ah,%%ah\n\t"
91  "jnz 2f\n\t"
92  "movw %%ax,%0\n\t"
93  "movw %%bx,%1\n\t"
94  "movw %%cx,%2\n\t"
95  "movw %%dx,%3\n\t"
96  "movw %%di,%4\n\t"
97  "movw %%si,%5\n\t"
98  "movw $1,%6\n\t"
99  "2:\n\t":"=m"(*(unsigned short *) pmyoutAX),
100  "=m"(*(unsigned short *) pmyoutBX),
101  "=m"(*(unsigned short *) pmyoutCX),
102  "=m"(*(unsigned short *) pmyoutDX),
103  "=m"(*(unsigned short *) pmyoutDI),
104  "=m"(*(unsigned short *) pmyoutSI),
105  "=m"(*(unsigned short *) pusSmapiOK)
106  :"m"(inBXCX), "m"(inDISI), "m"(g_usSmapiPort)
107  :"%eax", "%ebx", "%ecx", "%edx", "%edi",
108  "%esi");
109 
111  "myoutAX %x myoutBX %x myoutCX %x myoutDX %x myoutDI %x myoutSI %x usSmapiOK %x\n",
112  myoutAX, myoutBX, myoutCX, myoutDX, myoutDI, myoutSI,
113  usSmapiOK);
114  *outAX = myoutAX;
115  *outBX = myoutBX;
116  *outCX = myoutCX;
117  *outDX = myoutDX;
118  *outDI = myoutDI;
119  *outSI = myoutSI;
120 
121  retval = (usSmapiOK == 1) ? 0 : -EIO;
122  PRINTK_2(TRACE_SMAPI, "smapi::smapi_request exit retval %x\n", retval);
123  return retval;
124 }
125 
126 
128 {
129  int bRC = -EIO;
130  unsigned short usAX, usBX, usCX, usDX, usDI, usSI;
131  unsigned short ausDspBases[] = { 0x0030, 0x4E30, 0x8E30, 0xCE30, 0x0130, 0x0350, 0x0070, 0x0DB0 };
132  unsigned short ausUartBases[] = { 0x03F8, 0x02F8, 0x03E8, 0x02E8 };
133  unsigned short numDspBases = 8;
134  unsigned short numUartBases = 4;
135 
136  PRINTK_1(TRACE_SMAPI, "smapi::smapi_query_DSP_cfg entry\n");
137 
138  bRC = smapi_request(0x1802, 0x0000, 0, 0,
139  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
140  if (bRC) {
141  PRINTK_ERROR(KERN_ERR_MWAVE "smapi::smapi_query_DSP_cfg: Error: Could not get DSP Settings. Aborting.\n");
142  return bRC;
143  }
144 
145  PRINTK_1(TRACE_SMAPI, "smapi::smapi_query_DSP_cfg, smapi_request OK\n");
146 
147  pSettings->bDSPPresent = ((usBX & 0x0100) != 0);
148  pSettings->bDSPEnabled = ((usCX & 0x0001) != 0);
149  pSettings->usDspIRQ = usSI & 0x00FF;
150  pSettings->usDspDMA = (usSI & 0xFF00) >> 8;
151  if ((usDI & 0x00FF) < numDspBases) {
152  pSettings->usDspBaseIO = ausDspBases[usDI & 0x00FF];
153  } else {
154  pSettings->usDspBaseIO = 0;
155  }
157  "smapi::smapi_query_DSP_cfg get DSP Settings bDSPPresent %x bDSPEnabled %x usDspIRQ %x usDspDMA %x usDspBaseIO %x\n",
158  pSettings->bDSPPresent, pSettings->bDSPEnabled,
159  pSettings->usDspIRQ, pSettings->usDspDMA,
160  pSettings->usDspBaseIO);
161 
162  /* check for illegal values */
163  if ( pSettings->usDspBaseIO == 0 )
164  PRINTK_ERROR(KERN_ERR_MWAVE "smapi::smapi_query_DSP_cfg: Worry: DSP base I/O address is 0\n");
165  if ( pSettings->usDspIRQ == 0 )
166  PRINTK_ERROR(KERN_ERR_MWAVE "smapi::smapi_query_DSP_cfg: Worry: DSP IRQ line is 0\n");
167 
168  bRC = smapi_request(0x1804, 0x0000, 0, 0,
169  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
170  if (bRC) {
171  PRINTK_ERROR("smapi::smapi_query_DSP_cfg: Error: Could not get DSP modem settings. Aborting.\n");
172  return bRC;
173  }
174 
175  PRINTK_1(TRACE_SMAPI, "smapi::smapi_query_DSP_cfg, smapi_request OK\n");
176 
177  pSettings->bModemEnabled = ((usCX & 0x0001) != 0);
178  pSettings->usUartIRQ = usSI & 0x000F;
179  if (((usSI & 0xFF00) >> 8) < numUartBases) {
180  pSettings->usUartBaseIO = ausUartBases[(usSI & 0xFF00) >> 8];
181  } else {
182  pSettings->usUartBaseIO = 0;
183  }
184 
186  "smapi::smapi_query_DSP_cfg get DSP modem settings bModemEnabled %x usUartIRQ %x usUartBaseIO %x\n",
187  pSettings->bModemEnabled,
188  pSettings->usUartIRQ,
189  pSettings->usUartBaseIO);
190 
191  /* check for illegal values */
192  if ( pSettings->usUartBaseIO == 0 )
193  PRINTK_ERROR(KERN_ERR_MWAVE "smapi::smapi_query_DSP_cfg: Worry: UART base I/O address is 0\n");
194  if ( pSettings->usUartIRQ == 0 )
195  PRINTK_ERROR(KERN_ERR_MWAVE "smapi::smapi_query_DSP_cfg: Worry: UART IRQ line is 0\n");
196 
197  PRINTK_2(TRACE_SMAPI, "smapi::smapi_query_DSP_cfg exit bRC %x\n", bRC);
198 
199  return bRC;
200 }
201 
202 
204 {
205  int bRC = -EIO;
206  int i;
207  unsigned short usAX, usBX, usCX, usDX, usDI, usSI;
208  unsigned short ausDspBases[] = { 0x0030, 0x4E30, 0x8E30, 0xCE30, 0x0130, 0x0350, 0x0070, 0x0DB0 };
209  unsigned short ausUartBases[] = { 0x03F8, 0x02F8, 0x03E8, 0x02E8 };
210  unsigned short ausDspIrqs[] = { 5, 7, 10, 11, 15 };
211  unsigned short ausUartIrqs[] = { 3, 4 };
212 
213  unsigned short numDspBases = 8;
214  unsigned short numUartBases = 4;
215  unsigned short numDspIrqs = 5;
216  unsigned short numUartIrqs = 2;
217  unsigned short dspio_index = 0, uartio_index = 0;
218 
220  "smapi::smapi_set_DSP_cfg entry mwave_3780i_irq %x mwave_3780i_io %x mwave_uart_irq %x mwave_uart_io %x\n",
222 
223  if (mwave_3780i_io) {
224  for (i = 0; i < numDspBases; i++) {
225  if (mwave_3780i_io == ausDspBases[i])
226  break;
227  }
228  if (i == numDspBases) {
229  PRINTK_ERROR(KERN_ERR_MWAVE "smapi::smapi_set_DSP_cfg: Error: Invalid mwave_3780i_io address %x. Aborting.\n", mwave_3780i_io);
230  return bRC;
231  }
232  dspio_index = i;
233  }
234 
235  if (mwave_3780i_irq) {
236  for (i = 0; i < numDspIrqs; i++) {
237  if (mwave_3780i_irq == ausDspIrqs[i])
238  break;
239  }
240  if (i == numDspIrqs) {
241  PRINTK_ERROR(KERN_ERR_MWAVE "smapi::smapi_set_DSP_cfg: Error: Invalid mwave_3780i_irq %x. Aborting.\n", mwave_3780i_irq);
242  return bRC;
243  }
244  }
245 
246  if (mwave_uart_io) {
247  for (i = 0; i < numUartBases; i++) {
248  if (mwave_uart_io == ausUartBases[i])
249  break;
250  }
251  if (i == numUartBases) {
252  PRINTK_ERROR(KERN_ERR_MWAVE "smapi::smapi_set_DSP_cfg: Error: Invalid mwave_uart_io address %x. Aborting.\n", mwave_uart_io);
253  return bRC;
254  }
255  uartio_index = i;
256  }
257 
258 
259  if (mwave_uart_irq) {
260  for (i = 0; i < numUartIrqs; i++) {
261  if (mwave_uart_irq == ausUartIrqs[i])
262  break;
263  }
264  if (i == numUartIrqs) {
265  PRINTK_ERROR(KERN_ERR_MWAVE "smapi::smapi_set_DSP_cfg: Error: Invalid mwave_uart_irq %x. Aborting.\n", mwave_uart_irq);
266  return bRC;
267  }
268  }
269 
270  if (mwave_uart_irq || mwave_uart_io) {
271 
272  /* Check serial port A */
273  bRC = smapi_request(0x1402, 0x0000, 0, 0,
274  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
275  if (bRC) goto exit_smapi_request_error;
276  /* bRC == 0 */
277  if (usBX & 0x0100) { /* serial port A is present */
278  if (usCX & 1) { /* serial port is enabled */
279  if ((usSI & 0xFF) == mwave_uart_irq) {
280 #ifndef MWAVE_FUTZ_WITH_OTHER_DEVICES
282  "smapi::smapi_set_DSP_cfg: Serial port A irq %x conflicts with mwave_uart_irq %x\n", usSI & 0xFF, mwave_uart_irq);
283 #else
285  "smapi::smapi_set_DSP_cfg: Serial port A irq %x conflicts with mwave_uart_irq %x\n", usSI & 0xFF, mwave_uart_irq);
286 #endif
287 #ifdef MWAVE_FUTZ_WITH_OTHER_DEVICES
289  "smapi::smapi_set_DSP_cfg Disabling conflicting serial port\n");
290  bRC = smapi_request(0x1403, 0x0100, 0, usSI,
291  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
292  if (bRC) goto exit_smapi_request_error;
293  bRC = smapi_request(0x1402, 0x0000, 0, 0,
294  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
295  if (bRC) goto exit_smapi_request_error;
296 #else
297  goto exit_conflict;
298 #endif
299  } else {
300  if ((usSI >> 8) == uartio_index) {
301 #ifndef MWAVE_FUTZ_WITH_OTHER_DEVICES
303  "smapi::smapi_set_DSP_cfg: Serial port A base I/O address %x conflicts with mwave uart I/O %x\n", ausUartBases[usSI >> 8], ausUartBases[uartio_index]);
304 #else
306  "smapi::smapi_set_DSP_cfg: Serial port A base I/O address %x conflicts with mwave uart I/O %x\n", ausUartBases[usSI >> 8], ausUartBases[uartio_index]);
307 #endif
308 #ifdef MWAVE_FUTZ_WITH_OTHER_DEVICES
310  "smapi::smapi_set_DSP_cfg Disabling conflicting serial port A\n");
311  bRC = smapi_request (0x1403, 0x0100, 0, usSI,
312  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
313  if (bRC) goto exit_smapi_request_error;
314  bRC = smapi_request (0x1402, 0x0000, 0, 0,
315  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
316  if (bRC) goto exit_smapi_request_error;
317 #else
318  goto exit_conflict;
319 #endif
320  }
321  }
322  }
323  }
324 
325  /* Check serial port B */
326  bRC = smapi_request(0x1404, 0x0000, 0, 0,
327  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
328  if (bRC) goto exit_smapi_request_error;
329  /* bRC == 0 */
330  if (usBX & 0x0100) { /* serial port B is present */
331  if (usCX & 1) { /* serial port is enabled */
332  if ((usSI & 0xFF) == mwave_uart_irq) {
333 #ifndef MWAVE_FUTZ_WITH_OTHER_DEVICES
335  "smapi::smapi_set_DSP_cfg: Serial port B irq %x conflicts with mwave_uart_irq %x\n", usSI & 0xFF, mwave_uart_irq);
336 #else
338  "smapi::smapi_set_DSP_cfg: Serial port B irq %x conflicts with mwave_uart_irq %x\n", usSI & 0xFF, mwave_uart_irq);
339 #endif
340 #ifdef MWAVE_FUTZ_WITH_OTHER_DEVICES
342  "smapi::smapi_set_DSP_cfg Disabling conflicting serial port B\n");
343  bRC = smapi_request(0x1405, 0x0100, 0, usSI,
344  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
345  if (bRC) goto exit_smapi_request_error;
346  bRC = smapi_request(0x1404, 0x0000, 0, 0,
347  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
348  if (bRC) goto exit_smapi_request_error;
349 #else
350  goto exit_conflict;
351 #endif
352  } else {
353  if ((usSI >> 8) == uartio_index) {
354 #ifndef MWAVE_FUTZ_WITH_OTHER_DEVICES
356  "smapi::smapi_set_DSP_cfg: Serial port B base I/O address %x conflicts with mwave uart I/O %x\n", ausUartBases[usSI >> 8], ausUartBases[uartio_index]);
357 #else
359  "smapi::smapi_set_DSP_cfg: Serial port B base I/O address %x conflicts with mwave uart I/O %x\n", ausUartBases[usSI >> 8], ausUartBases[uartio_index]);
360 #endif
361 #ifdef MWAVE_FUTZ_WITH_OTHER_DEVICES
363  "smapi::smapi_set_DSP_cfg Disabling conflicting serial port B\n");
364  bRC = smapi_request (0x1405, 0x0100, 0, usSI,
365  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
366  if (bRC) goto exit_smapi_request_error;
367  bRC = smapi_request (0x1404, 0x0000, 0, 0,
368  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
369  if (bRC) goto exit_smapi_request_error;
370 #else
371  goto exit_conflict;
372 #endif
373  }
374  }
375  }
376  }
377 
378  /* Check IR port */
379  bRC = smapi_request(0x1700, 0x0000, 0, 0,
380  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
381  if (bRC) goto exit_smapi_request_error;
382  bRC = smapi_request(0x1704, 0x0000, 0, 0,
383  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
384  if (bRC) goto exit_smapi_request_error;
385  /* bRC == 0 */
386  if ((usCX & 0xff) != 0xff) { /* IR port not disabled */
387  if ((usCX & 0xff) == mwave_uart_irq) {
388 #ifndef MWAVE_FUTZ_WITH_OTHER_DEVICES
390  "smapi::smapi_set_DSP_cfg: IR port irq %x conflicts with mwave_uart_irq %x\n", usCX & 0xff, mwave_uart_irq);
391 #else
393  "smapi::smapi_set_DSP_cfg: IR port irq %x conflicts with mwave_uart_irq %x\n", usCX & 0xff, mwave_uart_irq);
394 #endif
395 #ifdef MWAVE_FUTZ_WITH_OTHER_DEVICES
397  "smapi::smapi_set_DSP_cfg Disabling conflicting IR port\n");
398  bRC = smapi_request(0x1701, 0x0100, 0, 0,
399  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
400  if (bRC) goto exit_smapi_request_error;
401  bRC = smapi_request(0x1700, 0, 0, 0,
402  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
403  if (bRC) goto exit_smapi_request_error;
404  bRC = smapi_request(0x1705, 0x01ff, 0, usSI,
405  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
406  if (bRC) goto exit_smapi_request_error;
407  bRC = smapi_request(0x1704, 0x0000, 0, 0,
408  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
409  if (bRC) goto exit_smapi_request_error;
410 #else
411  goto exit_conflict;
412 #endif
413  } else {
414  if ((usSI & 0xff) == uartio_index) {
415 #ifndef MWAVE_FUTZ_WITH_OTHER_DEVICES
417  "smapi::smapi_set_DSP_cfg: IR port base I/O address %x conflicts with mwave uart I/O %x\n", ausUartBases[usSI & 0xff], ausUartBases[uartio_index]);
418 #else
420  "smapi::smapi_set_DSP_cfg: IR port base I/O address %x conflicts with mwave uart I/O %x\n", ausUartBases[usSI & 0xff], ausUartBases[uartio_index]);
421 #endif
422 #ifdef MWAVE_FUTZ_WITH_OTHER_DEVICES
424  "smapi::smapi_set_DSP_cfg Disabling conflicting IR port\n");
425  bRC = smapi_request(0x1701, 0x0100, 0, 0,
426  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
427  if (bRC) goto exit_smapi_request_error;
428  bRC = smapi_request(0x1700, 0, 0, 0,
429  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
430  if (bRC) goto exit_smapi_request_error;
431  bRC = smapi_request(0x1705, 0x01ff, 0, usSI,
432  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
433  if (bRC) goto exit_smapi_request_error;
434  bRC = smapi_request(0x1704, 0x0000, 0, 0,
435  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
436  if (bRC) goto exit_smapi_request_error;
437 #else
438  goto exit_conflict;
439 #endif
440  }
441  }
442  }
443  }
444 
445  bRC = smapi_request(0x1802, 0x0000, 0, 0,
446  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
447  if (bRC) goto exit_smapi_request_error;
448 
449  if (mwave_3780i_io) {
450  usDI = dspio_index;
451  }
452  if (mwave_3780i_irq) {
453  usSI = (usSI & 0xff00) | mwave_3780i_irq;
454  }
455 
456  bRC = smapi_request(0x1803, 0x0101, usDI, usSI,
457  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
458  if (bRC) goto exit_smapi_request_error;
459 
460  bRC = smapi_request(0x1804, 0x0000, 0, 0,
461  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
462  if (bRC) goto exit_smapi_request_error;
463 
464  if (mwave_uart_io) {
465  usSI = (usSI & 0x00ff) | (uartio_index << 8);
466  }
467  if (mwave_uart_irq) {
468  usSI = (usSI & 0xff00) | mwave_uart_irq;
469  }
470  bRC = smapi_request(0x1805, 0x0101, 0, usSI,
471  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
472  if (bRC) goto exit_smapi_request_error;
473 
474  bRC = smapi_request(0x1802, 0x0000, 0, 0,
475  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
476  if (bRC) goto exit_smapi_request_error;
477 
478  bRC = smapi_request(0x1804, 0x0000, 0, 0,
479  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
480  if (bRC) goto exit_smapi_request_error;
481 
482 /* normal exit: */
483  PRINTK_1(TRACE_SMAPI, "smapi::smapi_set_DSP_cfg exit\n");
484  return 0;
485 
486 exit_conflict:
487  /* Message has already been printed */
488  return -EIO;
489 
490 exit_smapi_request_error:
491  PRINTK_ERROR(KERN_ERR_MWAVE "smapi::smapi_set_DSP_cfg exit on smapi_request error bRC %x\n", bRC);
492  return bRC;
493 }
494 
495 
497 {
498  int bRC = -EIO;
499  unsigned short usAX, usBX, usCX, usDX, usDI, usSI;
500  unsigned short usPowerFunction;
501 
502  PRINTK_2(TRACE_SMAPI, "smapi::smapi_set_DSP_power_state entry bOn %x\n", bOn);
503 
504  usPowerFunction = (bOn) ? 1 : 0;
505 
506  bRC = smapi_request(0x4901, 0x0000, 0, usPowerFunction,
507  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
508 
509  PRINTK_2(TRACE_SMAPI, "smapi::smapi_set_DSP_power_state exit bRC %x\n", bRC);
510 
511  return bRC;
512 }
513 
514 #if 0
515 static int SmapiQuerySystemID(void)
516 {
517  int bRC = -EIO;
518  unsigned short usAX = 0xffff, usBX = 0xffff, usCX = 0xffff,
519  usDX = 0xffff, usDI = 0xffff, usSI = 0xffff;
520 
521  printk("smapi::SmapiQUerySystemID entry\n");
522  bRC = smapi_request(0x0000, 0, 0, 0,
523  &usAX, &usBX, &usCX, &usDX, &usDI, &usSI);
524 
525  if (bRC == 0) {
526  printk("AX=%x, BX=%x, CX=%x, DX=%x, DI=%x, SI=%x\n",
527  usAX, usBX, usCX, usDX, usDI, usSI);
528  } else {
529  printk("smapi::SmapiQuerySystemID smapi_request error\n");
530  }
531 
532  return bRC;
533 }
534 #endif /* 0 */
535 
536 int smapi_init(void)
537 {
538  int retval = -EIO;
539  unsigned short usSmapiID = 0;
540  unsigned long flags;
541 
542  PRINTK_1(TRACE_SMAPI, "smapi::smapi_init entry\n");
543 
544  spin_lock_irqsave(&rtc_lock, flags);
545  usSmapiID = CMOS_READ(0x7C);
546  usSmapiID |= (CMOS_READ(0x7D) << 8);
547  spin_unlock_irqrestore(&rtc_lock, flags);
548  PRINTK_2(TRACE_SMAPI, "smapi::smapi_init usSmapiID %x\n", usSmapiID);
549 
550  if (usSmapiID == 0x5349) {
551  spin_lock_irqsave(&rtc_lock, flags);
552  g_usSmapiPort = CMOS_READ(0x7E);
553  g_usSmapiPort |= (CMOS_READ(0x7F) << 8);
554  spin_unlock_irqrestore(&rtc_lock, flags);
555  if (g_usSmapiPort == 0) {
556  PRINTK_ERROR("smapi::smapi_init, ERROR unable to read from SMAPI port\n");
557  } else {
559  "smapi::smapi_init, exit TRUE g_usSmapiPort %x\n",
560  g_usSmapiPort);
561  retval = 0;
562  //SmapiQuerySystemID();
563  }
564  } else {
565  PRINTK_ERROR("smapi::smapi_init, ERROR invalid usSmapiID\n");
566  retval = -ENXIO;
567  }
568 
569  return retval;
570 }