~xnox/debian/sid/dahdi-linux/nmu-659818

« back to all changes in this revision

Viewing changes to drivers/dahdi/voicebus/GpakApi.c

  • Committer: Bazaar Package Importer
  • Author(s): Mark Purcell, Tzafrir Cohen, Victor Seva
  • Date: 2009-05-20 07:22:46 UTC
  • mfrom: (1.1.1 upstream)
  • Revision ID: james.westby@ubuntu.com-20090520072246-y1ba8ofc81ykgf8z
Tags: 1:2.2.0~dfsg~rc4-1
* New upstream release

[ Tzafrir Cohen ]
* NOT RELEASED YET
* Dropped qozap as wcb4xxp provides that functionality.
* New upstream RC.
* Actually build OpenVox drivers.
* opvxa1200.c: rev. 1.4.12.4 (battery fixes and such)
* Fix '${match}' in udev rules file (hardwire).
* no_firmware_download: Disable downloading a binary kernel module at 
  build time.

[ Victor Seva ]
* fix debian/watch. 

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/*
 
2
 * Copyright (c) 2005, Adaptive Digital Technologies, Inc.
 
3
 *
 
4
 * File Name: GpakApi.c
 
5
 *
 
6
 * Description:
 
7
 *   This file contains user API functions to communicate with DSPs executing
 
8
 *   G.PAK software. The file is integrated into the host processor connected
 
9
 *   to C55X G.PAK DSPs via a Host Port Interface.
 
10
 *
 
11
 * Version: 1.0
 
12
 *
 
13
 * Revision History:
 
14
 *   06/15/05 - Initial release.
 
15
 *   11/15/2006  - 24 TDM-TDM Channels EC release
 
16
 *
 
17
 * This program has been released under the terms of the GPL version 2 by
 
18
 * permission of Adaptive Digital Technologies, Inc.
 
19
 *
 
20
 */
 
21
 
 
22
/*
 
23
 * See http://www.asterisk.org for more information about
 
24
 * the Asterisk project. Please do not directly contact
 
25
 * any of the maintainers of this project for assistance;
 
26
 * the project provides a web site, mailing lists and IRC
 
27
 * channels for your use.
 
28
 *
 
29
 * This program is free software, distributed under the terms of
 
30
 * the GNU General Public License Version 2 as published by the
 
31
 * Free Software Foundation. See the LICENSE file included with
 
32
 * this program for more details.
 
33
 */
 
34
 
 
35
#include "GpakHpi.h"
 
36
#include "GpakCust.h"
 
37
#include "GpakApi.h"
 
38
#include "gpakenum.h"
 
39
 
 
40
/* DSP to Host interface block offsets. */
 
41
#define REPLY_MSG_PNTR_OFFSET 0     /* I/F blk offset to Reply Msg Pointer */
 
42
#define CMD_MSG_PNTR_OFFSET 2       /* I/F blk offset to Command Msg Pointer */
 
43
#define EVENT_MSG_PNTR_OFFSET 4     /* I/F blk offset to Event Msg Pointer */
 
44
#define PKT_BUFR_MEM_OFFSET 6       /* I/F blk offset to Packet Buffer memory */
 
45
#define DSP_STATUS_OFFSET 8         /* I/F blk offset to DSP Status */
 
46
#define VERSION_ID_OFFSET 9         /* I/F blk offset to G.PAK Version Id */
 
47
#define MAX_CMD_MSG_LEN_OFFSET 10   /* I/F blk offset to Max Cmd Msg Length */
 
48
#define CMD_MSG_LEN_OFFSET 11       /* I/F blk offset to Command Msg Length */
 
49
#define REPLY_MSG_LEN_OFFSET 12     /* I/F blk offset to Reply Msg Length */
 
50
#define NUM_CHANNELS_OFFSET 13      /* I/F blk offset to Num Built Channels */
 
51
#define NUM_PKT_CHANNELS_OFFSET 14  /* I/F blk offset to Num Pkt Channels */
 
52
#define NUM_CONFERENCES_OFFSET 15   /* I/F blk offset to Num Conferences */
 
53
//#define CPU_USAGE_OFFSET_1MS 16     /* I/F blk offset to CPU Usage statistics */
 
54
#define CPU_USAGE_OFFSET 18         /* I/F blk offset to CPU Usage statistics */
 
55
//#define CPU_USAGE_OFFSET_10MS 20    /* I/F blk offset to CPU Usage statistics */
 
56
#define FRAMING_STATS_OFFSET 22     /* I/F blk offset to Framing statistics */
 
57
 
 
58
//#define GPAK_RELEASE_Rate rate10ms
 
59
// = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = 
 
60
// Macro to reconstruct a 32-bit value from two 16-bit values.
 
61
// Parameter p32: 32-bit-wide destination
 
62
// Parameter p16: 16-bit-wide source array of length 2 words
 
63
#define RECONSTRUCT_LONGWORD(p32, p16) p32 = (DSP_ADDRESS)p16[0]<<16; \
 
64
                                                                       p32 |= (unsigned long)p16[1]
 
65
// = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = 
 
66
 
 
67
/* DSP Status value definitions. */
 
68
#define DSP_INIT_STATUS 0x5555          /* DSP Initialized status value */
 
69
#define HOST_INIT_STATUS 0xAAAA         /* Host Initialized status value */
 
70
 
 
71
/* Circular packet buffer information structure offsets. */
 
72
#define CB_BUFR_BASE 0              /* pointer to base of circular buffer */
 
73
#define CB_BUFR_SIZE 2              /* size of buffer (words) */
 
74
#define CB_BUFR_PUT_INDEX 3         /* offset in buffer for next write */
 
75
#define CB_BUFR_TAKE_INDEX 4        /* offset in buffer for next read */
 
76
#define CIRC_BUFFER_INFO_STRUCT_SIZE 6 
 
77
 
 
78
/* Miscellaneous definitions. */
 
79
#define MSG_BUFFER_SIZE 100 /* size (words) of Host msg buffer */
 
80
#define WORD_BUFFER_SIZE 84  /* size of DSP Word buffer (words) */
 
81
 
 
82
#ifdef __TMS320C55XX__ // debug sections if not on host
 
83
#pragma DATA_SECTION(pDspIfBlk,"GPAKAPIDEBUG_SECT")
 
84
#pragma DATA_SECTION(MaxCmdMsgLen,"GPAKAPIDEBUG_SECT")
 
85
#pragma DATA_SECTION(MaxChannels,"GPAKAPIDEBUG_SECT")
 
86
#pragma DATA_SECTION(DlByteBufr,"GPAKAPIDEBUG_SECT")
 
87
#pragma DATA_SECTION(DlWordBufr,"GPAKAPIDEBUG_SECT")
 
88
#pragma DATA_SECTION(pEventFifoAddress,"GPAKAPIDEBUG_SECT")
 
89
#endif
 
90
 
 
91
/* Host variables related to Host to DSP interface. */
 
92
static DSP_ADDRESS pDspIfBlk[MAX_DSP_CORES];    /* DSP address of I/F block */
 
93
static DSP_WORD MaxCmdMsgLen[MAX_DSP_CORES]; /* max Cmd msg length (octets) */
 
94
static unsigned short int MaxChannels[MAX_DSP_CORES];    /* max num channels */
 
95
 
 
96
//static unsigned short int MaxPktChannels[MAX_DSP_CORES]; /* max num pkt channels */
 
97
//static unsigned short int MaxConfs[MAX_DSP_CORES];    /* max num conferences */
 
98
//static DSP_ADDRESS pPktInBufr[MAX_DSP_CORES][MAX_PKT_CHANNELS];  /* Pkt In buffer */
 
99
//static DSP_ADDRESS pPktOutBufr[MAX_DSP_CORES][MAX_PKT_CHANNELS]; /* Pkt Out buffer */
 
100
static DSP_ADDRESS pEventFifoAddress[MAX_DSP_CORES]; /* event fifo */
 
101
 
 
102
static unsigned char DlByteBufr[DOWNLOAD_BLOCK_SIZE * 2]; /* Dowload byte buf */
 
103
static DSP_WORD DlWordBufr[DOWNLOAD_BLOCK_SIZE];      /* Dowload word buffer */
 
104
 
 
105
 
 
106
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 
107
 * CheckDspReset - Check if the DSP was reset.
 
108
 *
 
109
 * FUNCTION
 
110
 *  This function determines if the DSP was reset and is ready. If reset
 
111
 *  occurred, it reads interface parameters and calculates DSP addresses.
 
112
 *
 
113
 * RETURNS
 
114
 *  -1 = DSP is not ready.
 
115
 *   0 = Reset did not occur.
 
116
 *   1 = Reset occurred.
 
117
 *
 
118
 */
 
119
static int CheckDspReset(
 
120
    int DspId               /* DSP Identifier (0 to MaxDSPCores-1) */
 
121
    )
 
122
{
 
123
    DSP_ADDRESS IfBlockPntr; /* Interface Block pointer */
 
124
    DSP_WORD DspStatus;      /* DSP Status */
 
125
    DSP_WORD DspChannels;    /* number of DSP channels */
 
126
    DSP_WORD  Temp[2];
 
127
 
 
128
    /* Read the pointer to the Interface Block. */
 
129
    gpakReadDspMemory(DspId, DSP_IFBLK_ADDRESS, 2, Temp);
 
130
    RECONSTRUCT_LONGWORD(IfBlockPntr, Temp);
 
131
 
 
132
    /* If the pointer is zero, return with an indication the DSP is not
 
133
       ready. */
 
134
    if (IfBlockPntr == 0)
 
135
        return (-1);
 
136
 
 
137
    /* Read the DSP's Status. */
 
138
    gpakReadDspMemory(DspId, IfBlockPntr + DSP_STATUS_OFFSET, 1, &DspStatus);
 
139
 
 
140
    /* If status indicates the DSP was reset, read the DSP's interface
 
141
       parameters and calculate DSP addresses. */
 
142
    if (DspStatus == DSP_INIT_STATUS ||
 
143
        ((DspStatus == HOST_INIT_STATUS) && (pDspIfBlk[DspId] == 0))) 
 
144
    {
 
145
        /* Save the address of the DSP's Interface Block. */
 
146
        pDspIfBlk[DspId] = IfBlockPntr;
 
147
 
 
148
        /* Read the DSP's interface parameters. */
 
149
        gpakReadDspMemory(DspId, IfBlockPntr + MAX_CMD_MSG_LEN_OFFSET, 1,
 
150
                          &(MaxCmdMsgLen[DspId]));
 
151
 
 
152
        /* read the number of configured DSP channels */
 
153
        gpakReadDspMemory(DspId, IfBlockPntr + NUM_CHANNELS_OFFSET, 1,
 
154
                          &DspChannels);
 
155
        if (DspChannels > MAX_CHANNELS)
 
156
            MaxChannels[DspId] = MAX_CHANNELS;
 
157
        else
 
158
            MaxChannels[DspId] = (unsigned short int) DspChannels;
 
159
 
 
160
        /* read the pointer to the event fifo info struct */
 
161
        gpakReadDspMemory(DspId, IfBlockPntr + EVENT_MSG_PNTR_OFFSET, 2, Temp);
 
162
        RECONSTRUCT_LONGWORD(pEventFifoAddress[DspId], Temp);
 
163
 
 
164
        /* Set the DSP Status to indicate the host recognized the reset. */
 
165
        DspStatus = HOST_INIT_STATUS;
 
166
        gpakWriteDspMemory(DspId, IfBlockPntr + DSP_STATUS_OFFSET, 1,
 
167
                           &DspStatus);
 
168
 
 
169
        /* Return with an indication that a reset occurred. */
 
170
        return (1);
 
171
    }
 
172
 
 
173
    /* If status doesn't indicate the host recognized a reset, return with an
 
174
       indication the DSP is not ready. */
 
175
    if ((DspStatus != HOST_INIT_STATUS) || (pDspIfBlk[DspId] == 0))
 
176
        return (-1);
 
177
 
 
178
    /* Return with an indication that a reset did not occur. */
 
179
    return (0);
 
180
}
 
181
 
 
182
 
 
183
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 
184
 * WriteDspCmdMessage - Write a Host Command/Request message to DSP.
 
185
 *
 
186
 * FUNCTION
 
187
 *  This function writes a Host Command/Request message into DSP memory and
 
188
 *  informs the DSP of the presence of the message.
 
189
 *
 
190
 * RETURNS
 
191
 *  -1 = Unable to write message (msg len or DSP Id invalid or DSP not ready)
 
192
 *   0 = Temporarily unable to write message (previous Cmd Msg busy)
 
193
 *   1 = Message written successfully
 
194
 *
 
195
 */
 
196
static int WriteDspCmdMessage(
 
197
    int DspId,                      /* DSP Identifier (0 to MaxDSPCores-1) */
 
198
    DSP_WORD *pMessage,          /* pointer to Command message */
 
199
    DSP_WORD MsgLength              /* length of message (octets) */
 
200
    )
 
201
{
 
202
    DSP_WORD CmdMsgLength;      /* current Cmd message length */
 
203
    DSP_WORD Temp[2];
 
204
    DSP_ADDRESS BufferPointer;     /* message buffer pointer */
 
205
 
 
206
    /* Check if the DSP was reset and is ready. */
 
207
    if (CheckDspReset(DspId) == -1)
 
208
        return (-1);
 
209
 
 
210
    /* Make sure the message length is valid. */
 
211
    if ((MsgLength < 1) || (MsgLength > MaxCmdMsgLen[DspId]))
 
212
        return (-1);
 
213
 
 
214
    /* Make sure a previous Command message is not in use by the DSP. */
 
215
    gpakReadDspMemory(DspId, pDspIfBlk[DspId] + CMD_MSG_LEN_OFFSET, 1,
 
216
                      &CmdMsgLength);
 
217
    if (CmdMsgLength != 0)
 
218
        return (0);
 
219
 
 
220
    /* Purge any previous Reply message that wasn't read. */
 
221
    gpakWriteDspMemory(DspId, pDspIfBlk[DspId] + REPLY_MSG_LEN_OFFSET, 1,
 
222
                       &CmdMsgLength);
 
223
 
 
224
    /* Copy the Command message into DSP memory. */
 
225
    gpakReadDspMemory(DspId, pDspIfBlk[DspId] + CMD_MSG_PNTR_OFFSET, 2, Temp);
 
226
    RECONSTRUCT_LONGWORD(BufferPointer, Temp);
 
227
    gpakWriteDspMemory(DspId, BufferPointer, (MsgLength + 1) / 2, pMessage);
 
228
 
 
229
    /* Store the message length in DSP's Command message length (flags DSP that
 
230
       a Command message is ready). */
 
231
    CmdMsgLength = MsgLength;
 
232
    gpakWriteDspMemory(DspId, pDspIfBlk[DspId] + CMD_MSG_LEN_OFFSET, 1,
 
233
                       &CmdMsgLength);
 
234
 
 
235
    /* Return with an indication the message was written. */
 
236
    return (1);
 
237
}
 
238
 
 
239
 
 
240
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 
241
 * ReadDspReplyMessage - Read a DSP Reply message from DSP.
 
242
 *
 
243
 * FUNCTION
 
244
 *  This function reads a DSP Reply message from DSP memory.
 
245
 *
 
246
 * RETURNS
 
247
 *  -1 = Unable to write message (msg len or DSP Id invalid or DSP not ready)
 
248
 *   0 = No message available (DSP Reply message empty)
 
249
 *   1 = Message read successfully (message and length stored in variables)
 
250
 *
 
251
 */
 
252
static int ReadDspReplyMessage(
 
253
    int DspId,                      /* DSP Identifier (0 to MaxDSPCores-1) */
 
254
    DSP_WORD *pMessage,             /* pointer to Reply message buffer */
 
255
    DSP_WORD *pMsgLength            /* pointer to msg length var (octets) */
 
256
    )
 
257
{
 
258
    DSP_WORD MsgLength;         /* message length */
 
259
    DSP_ADDRESS BufferPointer;  /* message buffer pointer */
 
260
    DSP_WORD Temp[2];
 
261
 
 
262
    /* Check if the DSP was reset and is ready. */
 
263
    if (CheckDspReset(DspId) == -1)
 
264
        return (-1);
 
265
 
 
266
    /* Check if a Reply message is ready. */
 
267
    gpakReadDspMemory(DspId, pDspIfBlk[DspId] + REPLY_MSG_LEN_OFFSET, 1,
 
268
                      &MsgLength);
 
269
    if (MsgLength == 0)
 
270
        return (0);
 
271
 
 
272
    /* Make sure the message length is valid. */
 
273
    if (MsgLength > *pMsgLength)
 
274
        return (-1);
 
275
 
 
276
    /* Copy the Reply message from DSP memory. */
 
277
    gpakReadDspMemory(DspId, pDspIfBlk[DspId] + REPLY_MSG_PNTR_OFFSET, 2, Temp);
 
278
    RECONSTRUCT_LONGWORD(BufferPointer, Temp);
 
279
    gpakReadDspMemory(DspId, BufferPointer, (MsgLength + 1) / 2, pMessage);
 
280
 
 
281
    /* Store the message length in the message length variable. */
 
282
    *pMsgLength = MsgLength;
 
283
 
 
284
    /* Indicate a Reply message is not ready. */
 
285
    MsgLength = 0;
 
286
    gpakWriteDspMemory(DspId, pDspIfBlk[DspId] + REPLY_MSG_LEN_OFFSET, 1,
 
287
                       &MsgLength);
 
288
 
 
289
    /* Return with an indication the message was read. */
 
290
    return (1);
 
291
}
 
292
 
 
293
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 
294
 * ReadCircBuffer - Read from a DSP circular buffer.
 
295
 *
 
296
 * FUNCTION
 
297
 *  This function reads a block of words from a DSP circular buffer. The Take
 
298
 *  address is incremented by the number of words read adjusting for buffer
 
299
 *  wrap.
 
300
 *
 
301
 * RETURNS
 
302
 *  nothing
 
303
 *
 
304
 */
 
305
static void ReadCircBuffer(
 
306
    int DspId,                  /* DSP Identifier (0 to MaxDSPCores-1) */
 
307
    DSP_ADDRESS BufrBaseAddress,   /* address of base of circular buffer */
 
308
    DSP_ADDRESS BufrLastAddress,   /* address of last word in buffer */
 
309
    DSP_ADDRESS *TakeAddress,      /* pointer to address in buffer for read */
 
310
    DSP_WORD *pWordBuffer,      /* pointer to buffer for words read */
 
311
    DSP_WORD NumWords           /* number of words to read */
 
312
    )
 
313
{
 
314
    DSP_WORD WordsTillEnd;      /* number of words until end of buffer */
 
315
 
 
316
    /* Determine the number of words from the start address until the end of the
 
317
       buffer. */
 
318
    WordsTillEnd = BufrLastAddress - *TakeAddress + 1;
 
319
 
 
320
    /* If a buffer wrap will occur, read the first part at the end of the
 
321
       buffer followed by the second part at the beginning of the buffer. */
 
322
    if (NumWords > WordsTillEnd)
 
323
    {
 
324
        gpakReadDspMemory(DspId, *TakeAddress, WordsTillEnd, pWordBuffer);
 
325
        gpakReadDspMemory(DspId, BufrBaseAddress, NumWords - WordsTillEnd,
 
326
                           &(pWordBuffer[WordsTillEnd]));
 
327
        *TakeAddress = BufrBaseAddress + NumWords - WordsTillEnd;
 
328
    }
 
329
 
 
330
    /* If a buffer wrap will not occur, read all words starting at the current
 
331
       take address in the buffer. */
 
332
    else
 
333
    {
 
334
        gpakReadDspMemory(DspId, *TakeAddress, NumWords, pWordBuffer);
 
335
        if (NumWords == WordsTillEnd)
 
336
            *TakeAddress = BufrBaseAddress;
 
337
        else
 
338
            *TakeAddress = *TakeAddress + NumWords;
 
339
    }
 
340
    return;
 
341
}
 
342
 
 
343
 
 
344
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 
345
 * VerifyReply - Verify the reply message is correct for the command sent.
 
346
 *
 
347
 * FUNCTION
 
348
 *  This function verifies correct reply message content for the command that
 
349
 *  was just sent.
 
350
 *
 
351
 * RETURNS
 
352
 *  0 = Incorrect
 
353
 *  1 = Correct
 
354
 *
 
355
 */
 
356
static int VerifyReply(
 
357
    DSP_WORD *pMsgBufr,     /* pointer to Reply message buffer */
 
358
    int CheckType,          /* reply check type */
 
359
    DSP_WORD CheckValue     /* reply check value */
 
360
    )
 
361
{
 
362
 
 
363
    /* Verify Channel or Conference Id. */
 
364
    if (CheckType == 1)
 
365
    {
 
366
        if (((pMsgBufr[1] >> 8) & 0xFF) != CheckValue)
 
367
            return (0);
 
368
    }
 
369
 
 
370
    /* Verify Test Mode Id. */
 
371
    else if (CheckType == 2)
 
372
    {
 
373
        if (pMsgBufr[1] != CheckValue)
 
374
            return (0);
 
375
    }
 
376
 
 
377
    /* Return with an indication of correct reply. */
 
378
    return (1);
 
379
}
 
380
 
 
381
 
 
382
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 
383
 * TransactCmd - Send a command to the DSP and receive it's reply.
 
384
 *
 
385
 * FUNCTION
 
386
 *  This function sends the specified command to the DSP and receives the DSP's
 
387
 *  reply.
 
388
 *
 
389
 * RETURNS
 
390
 *  Length of reply message (0 = Failure)
 
391
 *
 
392
 */
 
393
static unsigned int TransactCmd(
 
394
    int DspId,                  /* DSP Identifier (0 to MaxDSPCores-1) */
 
395
    DSP_WORD *pMsgBufr,         /* pointer to Cmd/Reply message buffer */
 
396
    DSP_WORD CmdLength,         /* length of command message (octets) */
 
397
    DSP_WORD ReplyType,         /* required type of reply message */
 
398
    DSP_WORD ReplyLength,       /* required length of reply message (octets) */
 
399
    int ReplyCheckType,         /* reply check type */
 
400
    DSP_WORD ReplyCheckValue    /* reply check value */
 
401
    )
 
402
{
 
403
    int FuncStatus;             /* function status */
 
404
    int LoopCount;              /* wait loop counter */
 
405
    DSP_WORD RcvReplyLength;    /* received Reply message length */
 
406
    DSP_WORD RcvReplyType;      /* received Reply message type code */
 
407
    DSP_WORD RetValue;          /* return value */
 
408
 
 
409
    /* Default the return value to indicate a failure. */
 
410
    RetValue = 0;
 
411
 
 
412
    /* Lock access to the DSP. */
 
413
    gpakLockAccess(DspId);
 
414
 
 
415
    /* Attempt to write the command message to the DSP. */
 
416
    LoopCount = 0;
 
417
    while ((FuncStatus = WriteDspCmdMessage(DspId, pMsgBufr, CmdLength)) != 1)
 
418
    {
 
419
        if (FuncStatus == -1)
 
420
            break;
 
421
        if (++LoopCount > MAX_WAIT_LOOPS)
 
422
            break;
 
423
        gpakHostDelay();
 
424
    }
 
425
 
 
426
    /* Attempt to read the reply message from the DSP if the command message was
 
427
       sent successfully. */
 
428
    if (FuncStatus == 1)
 
429
    {
 
430
        for (LoopCount = 0; LoopCount < MAX_WAIT_LOOPS; LoopCount++)
 
431
        {
 
432
            RcvReplyLength = MSG_BUFFER_SIZE * 2;
 
433
            FuncStatus = ReadDspReplyMessage(DspId, pMsgBufr, &RcvReplyLength);
 
434
            if (FuncStatus == 1)
 
435
            {
 
436
                RcvReplyType = (pMsgBufr[0] >> 8) & 0xFF;
 
437
                if ((RcvReplyLength >= ReplyLength) &&
 
438
                    (RcvReplyType == ReplyType) &&
 
439
                    VerifyReply(pMsgBufr, ReplyCheckType, ReplyCheckValue))
 
440
                {
 
441
                    RetValue = RcvReplyLength;
 
442
                    break;
 
443
                }
 
444
                else if (RcvReplyType == MSG_NULL_REPLY)
 
445
                    break;
 
446
            }
 
447
            else if (FuncStatus == -1)
 
448
                break;
 
449
            gpakHostDelay();
 
450
        }
 
451
    }
 
452
 
 
453
    /* Unlock access to the DSP. */
 
454
    gpakUnlockAccess(DspId);
 
455
 
 
456
    /* Return the length of the reply message (0 = failure). */
 
457
    return (RetValue);
 
458
}
 
459
 
 
460
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 
461
 * gpakConfigurePorts - Configure a DSP's serial ports.
 
462
 *
 
463
 * FUNCTION
 
464
 *  This function configures a DSP's serial ports.
 
465
 *
 
466
 * RETURNS
 
467
 *  Status code indicating success or a specific error.
 
468
 *
 
469
 */
 
470
gpakConfigPortStatus_t gpakConfigurePorts(
 
471
    unsigned short int DspId,       /* DSP Id (0 to MaxDSPCores-1) */
 
472
    const GpakPortConfig_t *pPortConfig,  /* pointer to Port Config info */
 
473
    GPAK_PortConfigStat_t *pStatus  /* pointer to Port Config Status */
 
474
    )
 
475
{
 
476
    DSP_WORD MsgBuffer[MSG_BUFFER_SIZE];    /* message buffer */
 
477
 
 
478
    /* Make sure the DSP Id is valid. */
 
479
    if (DspId >= MAX_DSP_CORES)
 
480
        return (CpsInvalidDsp);
 
481
 
 
482
    /* Build the Configure Serial Ports message. */
 
483
    MsgBuffer[0] = MSG_CONFIGURE_PORTS << 8;
 
484
    MsgBuffer[1] = (DSP_WORD)
 
485
                   ((pPortConfig->SlotsSelect1 << 12) |
 
486
                    ((pPortConfig->FirstBlockNum1 << 8) & 0x0F00) |
 
487
                    ((pPortConfig->SecBlockNum1 << 4) & 0x00F0));
 
488
    MsgBuffer[2] = (DSP_WORD) pPortConfig->FirstSlotMask1;
 
489
    MsgBuffer[3] = (DSP_WORD) pPortConfig->SecSlotMask1;
 
490
    MsgBuffer[4] = (DSP_WORD)
 
491
                   ((pPortConfig->SlotsSelect2 << 12) |
 
492
                    ((pPortConfig->FirstBlockNum2 << 8) & 0x0F00) |
 
493
                    ((pPortConfig->SecBlockNum2 << 4) & 0x00F0));
 
494
    MsgBuffer[5] = (DSP_WORD) pPortConfig->FirstSlotMask2;
 
495
    MsgBuffer[6] = (DSP_WORD) pPortConfig->SecSlotMask2;
 
496
    MsgBuffer[7] = (DSP_WORD)
 
497
                   ((pPortConfig->SlotsSelect3 << 12) |
 
498
                    ((pPortConfig->FirstBlockNum3 << 8) & 0x0F00) |
 
499
                    ((pPortConfig->SecBlockNum3 << 4) & 0x00F0));
 
500
    MsgBuffer[8] = (DSP_WORD) pPortConfig->FirstSlotMask3;
 
501
    MsgBuffer[9] = (DSP_WORD) pPortConfig->SecSlotMask3;
 
502
 
 
503
    MsgBuffer[10] = (DSP_WORD)
 
504
                   (((pPortConfig->DxDelay1 << 11) & 0x0800) |
 
505
                    ((pPortConfig->RxDataDelay1 << 9) & 0x0600) |
 
506
                    ((pPortConfig->TxDataDelay1 << 7) & 0x0180) |
 
507
                    ((pPortConfig->RxClockPolarity1 << 6) & 0x0040) |
 
508
                    ((pPortConfig->TxClockPolarity1 << 5) & 0x0020) |
 
509
                    ((pPortConfig->RxFrameSyncPolarity1 << 4) & 0x0010) |
 
510
                    ((pPortConfig->TxFrameSyncPolarity1 << 3) & 0x0008) |
 
511
                    ((pPortConfig->CompandingMode1 << 1) & 0x0006) |
 
512
                    (pPortConfig->SerialWordSize1 & 0x0001));
 
513
 
 
514
    MsgBuffer[11] = (DSP_WORD)
 
515
                   (((pPortConfig->DxDelay2 << 11) & 0x0800) |
 
516
                    ((pPortConfig->RxDataDelay2 << 9) & 0x0600) |
 
517
                    ((pPortConfig->TxDataDelay2 << 7) & 0x0180) |
 
518
                    ((pPortConfig->RxClockPolarity2 << 6) & 0x0040) |
 
519
                    ((pPortConfig->TxClockPolarity2 << 5) & 0x0020) |
 
520
                    ((pPortConfig->RxFrameSyncPolarity2 << 4) & 0x0010) |
 
521
                    ((pPortConfig->TxFrameSyncPolarity2 << 3) & 0x0008) |
 
522
                    ((pPortConfig->CompandingMode2 << 1) & 0x0006) |
 
523
                    (pPortConfig->SerialWordSize2 & 0x0001));
 
524
 
 
525
    MsgBuffer[12] = (DSP_WORD)
 
526
                   (((pPortConfig->DxDelay3 << 11) & 0x0800) |
 
527
                    ((pPortConfig->RxDataDelay3 << 9) & 0x0600) |
 
528
                    ((pPortConfig->TxDataDelay3 << 7) & 0x0180) |
 
529
                    ((pPortConfig->RxClockPolarity3 << 6) & 0x0040) |
 
530
                    ((pPortConfig->TxClockPolarity3 << 5) & 0x0020) |
 
531
                    ((pPortConfig->RxFrameSyncPolarity3 << 4) & 0x0010) |
 
532
                    ((pPortConfig->TxFrameSyncPolarity3 << 3) & 0x0008) |
 
533
                    ((pPortConfig->CompandingMode3 << 1) & 0x0006) |
 
534
                    (pPortConfig->SerialWordSize3 & 0x0001));
 
535
 
 
536
    MsgBuffer[13] = (DSP_WORD) pPortConfig->ThirdSlotMask1;
 
537
    MsgBuffer[14] = (DSP_WORD) pPortConfig->FouthSlotMask1;
 
538
    MsgBuffer[15] = (DSP_WORD) pPortConfig->FifthSlotMask1;
 
539
    MsgBuffer[16] = (DSP_WORD) pPortConfig->SixthSlotMask1;
 
540
    MsgBuffer[17] = (DSP_WORD) pPortConfig->SevenSlotMask1;
 
541
    MsgBuffer[18] = (DSP_WORD) pPortConfig->EightSlotMask1;
 
542
    
 
543
    MsgBuffer[19] = (DSP_WORD) pPortConfig->ThirdSlotMask2;;
 
544
    MsgBuffer[20] = (DSP_WORD) pPortConfig->FouthSlotMask2;            
 
545
    MsgBuffer[21] = (DSP_WORD) pPortConfig->FifthSlotMask2;;             
 
546
    MsgBuffer[22] = (DSP_WORD) pPortConfig->SixthSlotMask2;            
 
547
    MsgBuffer[23] = (DSP_WORD) pPortConfig->SevenSlotMask2;;             
 
548
    MsgBuffer[24] = (DSP_WORD) pPortConfig->EightSlotMask2;            
 
549
 
 
550
    MsgBuffer[25] = (DSP_WORD) pPortConfig->ThirdSlotMask3;;
 
551
    MsgBuffer[26] = (DSP_WORD) pPortConfig->FouthSlotMask3;            
 
552
    MsgBuffer[27] = (DSP_WORD) pPortConfig->FifthSlotMask3;;             
 
553
    MsgBuffer[28] = (DSP_WORD) pPortConfig->SixthSlotMask3;            
 
554
    MsgBuffer[29] = (DSP_WORD) pPortConfig->SevenSlotMask3;;             
 
555
    MsgBuffer[30] = (DSP_WORD) pPortConfig->EightSlotMask3;            
 
556
 
 
557
 
 
558
    /* Attempt to send the Configure Serial Ports message to the DSP and receive
 
559
       it's reply. */
 
560
        if (!TransactCmd(DspId, MsgBuffer, 62, MSG_CONFIG_PORTS_REPLY, 4, 0, 0))
 
561
        return (CpsDspCommFailure);
 
562
 
 
563
    /* Return with an indication of success or failure based on the return
 
564
       status in the reply message. */
 
565
    *pStatus = (GPAK_PortConfigStat_t) (MsgBuffer[1] & 0xFF);
 
566
    if (*pStatus == Pc_Success)
 
567
        return (CpsSuccess);
 
568
    else
 
569
        return (CpsParmError);
 
570
}
 
571
EXPORT_SYMBOL(gpakConfigurePorts);
 
572
 
 
573
 
 
574
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 
575
 * gpakConfigureChannel - Configure a DSP's Channel.
 
576
 *
 
577
 * FUNCTION
 
578
 *  This function configures a DSP's Channel.
 
579
 *
 
580
 * RETURNS
 
581
 *  Status code indicating success or a specific error.
 
582
 *
 
583
 */
 
584
gpakConfigChanStatus_t gpakConfigureChannel(
 
585
    unsigned short int DspId,           /* DSP Id (0 to MaxDSPCores-1) */
 
586
    unsigned short int ChannelId,       /* Channel Id (0 to MaxChannels-1) */
 
587
    GpakChanType ChannelType,           /* Channel Type */
 
588
    GpakChannelConfig_t *pChanConfig,   /* pointer to Channel Config info */
 
589
    GPAK_ChannelConfigStat_t *pStatus   /* pointer to Channel Config Status */
 
590
    )
 
591
{
 
592
    DSP_WORD MsgBuffer[MSG_BUFFER_SIZE];    /* message buffer */
 
593
    DSP_WORD MsgLength;                     /* message length */
 
594
 
 
595
    /* Make sure the DSP Id is valid. */
 
596
    if (DspId >= MAX_DSP_CORES)
 
597
        return (CcsInvalidDsp);
 
598
 
 
599
    /* Make sure the Channel Id is valid. */
 
600
    if (ChannelId >= MaxChannels[DspId])
 
601
        return (CcsInvalidChannel);
 
602
 
 
603
    /* Build the Configure Channel message based on the Channel Type. */
 
604
    switch (ChannelType)
 
605
    {
 
606
 
 
607
    /* PCM to Packet channel type. */
 
608
    case tdmToTdm:
 
609
 
 
610
        MsgBuffer[2] = (DSP_WORD)
 
611
                       ((pChanConfig->PcmInPortA << 8) |
 
612
                        (pChanConfig->PcmInSlotA & 0xFF));
 
613
        MsgBuffer[3] = (DSP_WORD)
 
614
                       ((pChanConfig->PcmOutPortA << 8) |
 
615
                        (pChanConfig->PcmOutSlotA & 0xFF));
 
616
 
 
617
        MsgBuffer[4] = (DSP_WORD)
 
618
                       ((pChanConfig->PcmInPortB << 8) |
 
619
                        (pChanConfig->PcmInSlotB & 0xFF));
 
620
        MsgBuffer[5] = (DSP_WORD)
 
621
                       ((pChanConfig->PcmOutPortB << 8) |
 
622
                        (pChanConfig->PcmOutSlotB & 0xFF));
 
623
 
 
624
        MsgBuffer[6] = (DSP_WORD)
 
625
                       (
 
626
                       ((pChanConfig->FaxCngDetB <<11) & 0x0800)  |
 
627
                       ((pChanConfig->FaxCngDetA <<10) & 0x0400)  |
 
628
                       ((pChanConfig->MuteToneB << 9) & 0x0200)  |
 
629
                       ((pChanConfig->MuteToneA << 8) & 0x0100)  |
 
630
                       ((pChanConfig->FrameRate << 6)  & 0x00C0) |  
 
631
                       ((pChanConfig->ToneTypesB << 5) & 0x0020) |
 
632
                       ((pChanConfig->ToneTypesA << 4) & 0x0010) |
 
633
                       ((pChanConfig->SoftwareCompand & 3) << 2) |
 
634
                        (pChanConfig->EcanEnableB << 1) | 
 
635
                        (pChanConfig->EcanEnableA & 1)
 
636
                        );
 
637
                        
 
638
        MsgBuffer[7]   = (DSP_WORD)
 
639
                         pChanConfig->EcanParametersA.EcanTapLength;       
 
640
        MsgBuffer[8]   = (DSP_WORD)
 
641
                         pChanConfig->EcanParametersA.EcanNlpType;         
 
642
        MsgBuffer[9]  = (DSP_WORD)
 
643
                         pChanConfig->EcanParametersA.EcanAdaptEnable;     
 
644
        MsgBuffer[10]  = (DSP_WORD)
 
645
                         pChanConfig->EcanParametersA.EcanG165DetEnable;   
 
646
        MsgBuffer[11]  = (DSP_WORD)
 
647
                         pChanConfig->EcanParametersA.EcanDblTalkThresh;   
 
648
        MsgBuffer[12]  = (DSP_WORD)
 
649
                         pChanConfig->EcanParametersA.EcanNlpThreshold;    
 
650
        MsgBuffer[13]  = (DSP_WORD)
 
651
                         pChanConfig->EcanParametersA.EcanNlpConv;    
 
652
        MsgBuffer[14]  = (DSP_WORD)
 
653
                         pChanConfig->EcanParametersA.EcanNlpUnConv;    
 
654
        MsgBuffer[15]  = (DSP_WORD)
 
655
                         pChanConfig->EcanParametersA.EcanNlpMaxSuppress;    
 
656
 
 
657
        MsgBuffer[16]  = (DSP_WORD)
 
658
                         pChanConfig->EcanParametersA.EcanCngThreshold;    
 
659
        MsgBuffer[17]  = (DSP_WORD)
 
660
                         pChanConfig->EcanParametersA.EcanAdaptLimit;      
 
661
        MsgBuffer[18]  = (DSP_WORD)
 
662
                         pChanConfig->EcanParametersA.EcanCrossCorrLimit;  
 
663
        MsgBuffer[19]  = (DSP_WORD)
 
664
                         pChanConfig->EcanParametersA.EcanNumFirSegments;  
 
665
        MsgBuffer[20]  = (DSP_WORD)
 
666
                         pChanConfig->EcanParametersA.EcanFirSegmentLen;   
 
667
 
 
668
        MsgBuffer[21]   = (DSP_WORD)
 
669
                         pChanConfig->EcanParametersB.EcanTapLength;       
 
670
        MsgBuffer[22]   = (DSP_WORD)
 
671
                         pChanConfig->EcanParametersB.EcanNlpType;         
 
672
        MsgBuffer[23]  = (DSP_WORD)
 
673
                         pChanConfig->EcanParametersB.EcanAdaptEnable;     
 
674
        MsgBuffer[24]  = (DSP_WORD)
 
675
                         pChanConfig->EcanParametersB.EcanG165DetEnable;   
 
676
        MsgBuffer[25]  = (DSP_WORD)
 
677
                         pChanConfig->EcanParametersB.EcanDblTalkThresh;   
 
678
        MsgBuffer[26]  = (DSP_WORD)
 
679
                         pChanConfig->EcanParametersB.EcanNlpThreshold;    
 
680
        MsgBuffer[27]  = (DSP_WORD)
 
681
                         pChanConfig->EcanParametersB.EcanNlpConv;    
 
682
        MsgBuffer[28]  = (DSP_WORD)
 
683
                         pChanConfig->EcanParametersB.EcanNlpUnConv;    
 
684
        MsgBuffer[29]  = (DSP_WORD)
 
685
                         pChanConfig->EcanParametersB.EcanNlpMaxSuppress;    
 
686
        MsgBuffer[30]  = (DSP_WORD)
 
687
                         pChanConfig->EcanParametersB.EcanCngThreshold;    
 
688
        MsgBuffer[31]  = (DSP_WORD)
 
689
                         pChanConfig->EcanParametersB.EcanAdaptLimit;      
 
690
        MsgBuffer[32]  = (DSP_WORD)
 
691
                         pChanConfig->EcanParametersB.EcanCrossCorrLimit;  
 
692
        MsgBuffer[33]  = (DSP_WORD)
 
693
                         pChanConfig->EcanParametersB.EcanNumFirSegments;  
 
694
        MsgBuffer[34]  = (DSP_WORD)
 
695
                         pChanConfig->EcanParametersB.EcanFirSegmentLen;   
 
696
 
 
697
        MsgBuffer[35] = (DSP_WORD)
 
698
                       (
 
699
                       ((pChanConfig->EcanParametersB.EcanReconvergenceCheckEnable <<5) & 0x20)  |
 
700
                       ((pChanConfig->EcanParametersA.EcanReconvergenceCheckEnable <<4) & 0x10)  |
 
701
                       ((pChanConfig->EcanParametersB.EcanTandemOperationEnable <<3) & 0x8)  |
 
702
                       ((pChanConfig->EcanParametersA.EcanTandemOperationEnable <<2) & 0x4)  |
 
703
                       ((pChanConfig->EcanParametersB.EcanMixedFourWireMode << 1) & 0x2) | 
 
704
                        (pChanConfig->EcanParametersA.EcanMixedFourWireMode & 1)
 
705
                        );
 
706
        MsgBuffer[36]  = (DSP_WORD)
 
707
                         pChanConfig->EcanParametersA.EcanMaxDoubleTalkThres;   
 
708
 
 
709
        MsgBuffer[37]  = (DSP_WORD)
 
710
                         pChanConfig->EcanParametersB.EcanMaxDoubleTalkThres;   
 
711
 
 
712
        MsgLength = 76; // byte number == 38*2 
 
713
        break;
 
714
 
 
715
 
 
716
    /* Unknown (invalid) channel type. */
 
717
    default:
 
718
        *pStatus = Cc_InvalidChannelType;
 
719
        return (CcsParmError);
 
720
    }
 
721
 
 
722
    MsgBuffer[0] = MSG_CONFIGURE_CHANNEL << 8;
 
723
    MsgBuffer[1] = (DSP_WORD) ((ChannelId << 8) | (ChannelType & 0xFF));
 
724
 
 
725
    /* Attempt to send the Configure Channel message to the DSP and receive it's
 
726
       reply. */
 
727
        if (!TransactCmd(DspId, MsgBuffer, MsgLength, MSG_CONFIG_CHAN_REPLY, 4, 1,
 
728
                     (DSP_WORD) ChannelId))
 
729
        return (CcsDspCommFailure);
 
730
 
 
731
    /* Return with an indication of success or failure based on the return
 
732
       status in the reply message. */
 
733
    *pStatus = (GPAK_ChannelConfigStat_t) (MsgBuffer[1] & 0xFF);
 
734
    if (*pStatus == Cc_Success)
 
735
        return (CcsSuccess);
 
736
    else
 
737
        return (CcsParmError);
 
738
}
 
739
EXPORT_SYMBOL(gpakConfigureChannel);
 
740
 
 
741
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 
742
 * gpakTearDownChannel - Tear Down a DSP's Channel.
 
743
 *
 
744
 * FUNCTION
 
745
 *  This function tears down a DSP's Channel.
 
746
 *
 
747
 * RETURNS
 
748
 *  Status code indicating success or a specific error.
 
749
 *
 
750
 */
 
751
gpakTearDownStatus_t gpakTearDownChannel(
 
752
    unsigned short int DspId,           /* DSP Id (0 to MaxDSPCores-1) */
 
753
    unsigned short int ChannelId,       /* Channel Id (0 to MaxChannels-1) */
 
754
    GPAK_TearDownChanStat_t *pStatus    /* pointer to Tear Down Status */
 
755
    )
 
756
{
 
757
    DSP_WORD MsgBuffer[MSG_BUFFER_SIZE];    /* message buffer */
 
758
 
 
759
    /* Make sure the DSP Id is valid. */
 
760
    if (DspId >= MAX_DSP_CORES)
 
761
        return (TdsInvalidDsp);
 
762
 
 
763
    /* Make sure the Channel Id is valid. */
 
764
    if (ChannelId >= MaxChannels[DspId])
 
765
        return (TdsInvalidChannel);
 
766
 
 
767
    /* Build the Tear Down Channel message. */
 
768
    MsgBuffer[0] = MSG_TEAR_DOWN_CHANNEL << 8;
 
769
    MsgBuffer[1] = (DSP_WORD) (ChannelId << 8);
 
770
 
 
771
    /* Attempt to send the Tear Down Channel message to the DSP and receive it's
 
772
       reply. */
 
773
        if (!TransactCmd(DspId, MsgBuffer, 3, MSG_TEAR_DOWN_REPLY, 4, 1,
 
774
                         (DSP_WORD) ChannelId))
 
775
        return (TdsDspCommFailure);
 
776
 
 
777
    /* Return with an indication of success or failure based on the return
 
778
       status in the reply message. */
 
779
    *pStatus = (GPAK_TearDownChanStat_t) (MsgBuffer[1] & 0xFF);
 
780
    if (*pStatus == Td_Success)
 
781
        return (TdsSuccess);
 
782
    else
 
783
        return (TdsError);
 
784
}
 
785
 
 
786
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 
787
 * gpakAlgControl - Control an Algorithm.
 
788
 *
 
789
 * FUNCTION
 
790
 *  This function controls an Algorithm
 
791
 *
 
792
 * RETURNS
 
793
 *  Status code indicating success or a specific error.
 
794
 *
 
795
 */
 
796
gpakAlgControlStat_t gpakAlgControl(
 
797
    unsigned short int  DspId,          // DSP identifier
 
798
    unsigned short int  ChannelId,              // channel identifier
 
799
    GpakAlgCtrl_t       ControlCode,    // algorithm control code
 
800
    GPAK_AlgControlStat_t *pStatus      // pointer to return status
 
801
    )
 
802
{
 
803
    DSP_WORD MsgBuffer[MSG_BUFFER_SIZE];    /* message buffer */
 
804
    
 
805
    /* Make sure the DSP Id is valid. */
 
806
    if (DspId >= MAX_DSP_CORES)
 
807
        return (AcInvalidDsp);
 
808
 
 
809
    /* Make sure the Channel Id is valid. */
 
810
    if (ChannelId >= MaxChannels[DspId])
 
811
        return (AcInvalidChannel);
 
812
 
 
813
    MsgBuffer[0] = MSG_ALG_CONTROL << 8;
 
814
    MsgBuffer[1] = (DSP_WORD) ((ChannelId << 8) | (ControlCode & 0xFF));
 
815
 
 
816
    /* Attempt to send the Tear Down Channel message to the DSP and receive it's
 
817
       reply. */
 
818
        //need_reply_len;       
 
819
        if (!TransactCmd(DspId, MsgBuffer, 4, MSG_ALG_CONTROL_REPLY, 4, 1,  
 
820
                         (DSP_WORD) ChannelId))
 
821
        return (AcDspCommFailure);
 
822
 
 
823
    /* Return with an indication of success or failure based on the return
 
824
       status in the reply message. */
 
825
    *pStatus = (GPAK_AlgControlStat_t) (MsgBuffer[1] & 0xFF);
 
826
    if (*pStatus == Ac_Success)
 
827
        return (AcSuccess);
 
828
    else
 
829
        return (AcParmError);
 
830
 
 
831
}
 
832
EXPORT_SYMBOL(gpakAlgControl);
 
833
 
 
834
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 
835
 * gpakReadEventFIFOMessage - read from the event fifo
 
836
 * 
 
837
 * FUNCTION
 
838
 *  This function reads a single event from the event fifo if one is available
 
839
 * 
 
840
 * RETURNS
 
841
 *  Status  code indicating success or a specific error.
 
842
 *
 
843
 * Notes: This function should be called in a loop until the return status 
 
844
 *        indicates that the fifo is empty.
 
845
 *      
 
846
 *        If the event code equals "EventLoopbackTeardownComplete", then the 
 
847
 *        contents of *pChannelId hold the coderBlockId that was assigned to
 
848
 *        the loopback coder that was torn down.
 
849
 */
 
850
gpakReadEventFIFOMessageStat_t gpakReadEventFIFOMessage(
 
851
    unsigned short int      DspId,          // DSP identifier
 
852
    unsigned short int      *pChannelId,    // pointer to channel identifier
 
853
    GpakAsyncEventCode_t    *pEventCode,    // pointer to Event Code
 
854
    GpakAsyncEventData_t    *pEventData     // pointer to Event Data Struct
 
855
    )
 
856
{
 
857
    DSP_WORD WordBuffer[WORD_BUFFER_SIZE];  /* DSP words buffer */
 
858
    GpakAsyncEventCode_t EventCode;         /* DSP's event code */
 
859
    DSP_WORD EventDataLength;               /* Length of event to read */
 
860
    DSP_WORD ChannelId;                     /* DSP's channel Id */
 
861
    DSP_ADDRESS EventInfoAddress;     /* address of EventFIFO info structure */
 
862
    DSP_ADDRESS BufrBaseAddress;      /* base address of EventFIFO buffer */
 
863
    DSP_ADDRESS BufrLastAddress;      /* last address of EventFIFO buffer */
 
864
    DSP_ADDRESS TakeAddress;          /* current take address in fifo buffer */
 
865
    DSP_WORD BufrSize;      /* size (in words) of event FIFO buffer */
 
866
    DSP_WORD PutIndex;      /* event fifo put index */
 
867
    DSP_WORD TakeIndex;     /* event fifo take index */
 
868
    DSP_WORD WordsReady;    /* number words ready for read out of event fifo */
 
869
    DSP_WORD EventError;    /* flag indicating error with event fifo msg  */
 
870
 
 
871
    /* Make sure the DSP Id is valid. */
 
872
    if (DspId >= MAX_DSP_CORES)
 
873
        return (RefInvalidDsp);
 
874
 
 
875
    /* Lock access to the DSP. */
 
876
    gpakLockAccess(DspId);
 
877
 
 
878
    /* Check if the DSP was reset and is ready. */
 
879
    if (CheckDspReset(DspId) == -1)
 
880
    {
 
881
        gpakUnlockAccess(DspId);
 
882
        return (RefDspCommFailure);
 
883
    }
 
884
 
 
885
    /* Check if an event message is ready in the DSP. */
 
886
    EventInfoAddress = pEventFifoAddress[DspId];
 
887
    gpakReadDspMemory(DspId, EventInfoAddress, CIRC_BUFFER_INFO_STRUCT_SIZE, 
 
888
                                                                 WordBuffer);
 
889
    RECONSTRUCT_LONGWORD(BufrBaseAddress, ((DSP_WORD *)&WordBuffer[CB_BUFR_BASE]));
 
890
    BufrSize = WordBuffer[CB_BUFR_SIZE];
 
891
    PutIndex = WordBuffer[CB_BUFR_PUT_INDEX];
 
892
    TakeIndex = WordBuffer[CB_BUFR_TAKE_INDEX];
 
893
    if (PutIndex >= TakeIndex)
 
894
        WordsReady = PutIndex - TakeIndex;
 
895
    else
 
896
        WordsReady = PutIndex + BufrSize - TakeIndex;
 
897
 
 
898
    if (WordsReady < 2)
 
899
    {
 
900
        gpakUnlockAccess(DspId);
 
901
        return (RefNoEventAvail);
 
902
    }
 
903
 
 
904
    /* Read the event header from the DSP's Event FIFO. */
 
905
    TakeAddress = BufrBaseAddress + TakeIndex;
 
906
    BufrLastAddress = BufrBaseAddress + BufrSize - 1;
 
907
    ReadCircBuffer(DspId, BufrBaseAddress, BufrLastAddress, &TakeAddress,
 
908
                   WordBuffer, 2);
 
909
    TakeIndex += 2;
 
910
    if (TakeIndex >= BufrSize)
 
911
        TakeIndex -= BufrSize;
 
912
 
 
913
    ChannelId = (WordBuffer[0] >> 8) & 0xFF;
 
914
    EventCode = (GpakAsyncEventCode_t)(WordBuffer[0] & 0xFF);
 
915
    EventDataLength = WordBuffer[1];
 
916
    EventError = 0;
 
917
 
 
918
    switch (EventCode)
 
919
    {
 
920
        case EventToneDetect:
 
921
            if (EventDataLength > WORD_BUFFER_SIZE)
 
922
            {
 
923
                gpakUnlockAccess(DspId);
 
924
                return (RefInvalidEvent);
 
925
            }
 
926
            ReadCircBuffer(DspId, BufrBaseAddress, BufrLastAddress, &TakeAddress,
 
927
                   WordBuffer, EventDataLength);
 
928
            pEventData->toneEvent.ToneCode = (GpakToneCodes_t)
 
929
                                                (WordBuffer[0] & 0xFF);
 
930
            pEventData->toneEvent.ToneDuration = WordBuffer[1];
 
931
            pEventData->toneEvent.Direction = WordBuffer[2];
 
932
            pEventData->toneEvent.DebugToneStatus = WordBuffer[3];
 
933
            TakeIndex += EventDataLength;
 
934
            if (TakeIndex >= BufrSize)
 
935
                TakeIndex -= BufrSize;
 
936
            if (EventDataLength != 4)
 
937
                EventError = 1;
 
938
            break;
 
939
 
 
940
        default:
 
941
            EventError = 1;
 
942
            break;
 
943
    };
 
944
 
 
945
    /* Update the Take index in the DSP's Packet Out buffer information. */
 
946
    gpakWriteDspMemory(DspId, EventInfoAddress + CB_BUFR_TAKE_INDEX, 1,
 
947
                       &TakeIndex);
 
948
 
 
949
    /* Unlock access to the DSP. */
 
950
    gpakUnlockAccess(DspId);
 
951
 
 
952
    if (EventError)
 
953
        return(RefInvalidEvent);
 
954
 
 
955
    *pChannelId = ChannelId;
 
956
    *pEventCode = EventCode;
 
957
    return(RefEventAvail);
 
958
 
 
959
}
 
960
 
 
961
 
 
962
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 
963
 * gpakPingDsp - ping the DSP to see if it's alive
 
964
 * 
 
965
 * FUNCTION
 
966
 *  This function checks if the DSP is still communicating with the host
 
967
 *  and returns the DSP SW version
 
968
 * 
 
969
 * RETURNS
 
970
 *  Status  code indicating success or a specific error.
 
971
 */
 
972
gpakPingDspStat_t gpakPingDsp(
 
973
    unsigned short int      DspId,          // DSP identifier
 
974
    unsigned short int      *pDspSwVersion  // DSP software version
 
975
    )
 
976
{
 
977
    DSP_WORD MsgBuffer[MSG_BUFFER_SIZE];    /* message buffer */
 
978
    DSP_WORD DspStatus;                     /* DSP's reply status */
 
979
 
 
980
    /* Make sure the DSP Id is valid. */
 
981
    if (DspId >= MAX_DSP_CORES)
 
982
        return (PngInvalidDsp);
 
983
 
 
984
    /* send value of 1, DSP increments it */
 
985
    MsgBuffer[0] = (MSG_PING << 8);
 
986
 
 
987
    /* Attempt to send the ping message to the DSP and receive it's
 
988
       reply. */
 
989
        if (!TransactCmd(DspId, MsgBuffer, 1, MSG_PING_REPLY, 6, 0, 0))
 
990
        return (PngDspCommFailure);
 
991
 
 
992
    /* Return with an indication of success or failure based on the return
 
993
       status in the reply message. */
 
994
    DspStatus = (MsgBuffer[1] & 0xFF);
 
995
    if (DspStatus == 0)
 
996
    {
 
997
        *pDspSwVersion = MsgBuffer[2];
 
998
        return (PngSuccess);
 
999
    }
 
1000
    else
 
1001
        return (PngDspCommFailure);
 
1002
}
 
1003
EXPORT_SYMBOL(gpakPingDsp);
 
1004
 
 
1005
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 
1006
 * gpakSerialTxFixedValue - transmit a fixed value on a timeslot
 
1007
 * 
 
1008
 * FUNCTION
 
1009
 *  This function controls transmission of a fixed value out onto a serial 
 
1010
 *  port's timeslot.
 
1011
 * 
 
1012
 * RETURNS
 
1013
 *  Status  code indicating success or a specific error.
 
1014
 */
 
1015
gpakSerialTxFixedValueStat_t gpakSerialTxFixedValue(
 
1016
    unsigned short int      DspId,          // DSP identifier
 
1017
    unsigned short int      ChannelId,      // channel identifier
 
1018
    GpakSerialPort_t        PcmOutPort,     // PCM Output Serial Port Id
 
1019
    unsigned short int      PcmOutSlot,     // PCM Output Time Slot
 
1020
    unsigned short int      Value,          // 16-bit value 
 
1021
    GpakActivation          State                   // activation state
 
1022
    )
 
1023
{
 
1024
    DSP_WORD MsgBuffer[MSG_BUFFER_SIZE];    /* message buffer */
 
1025
    DSP_WORD DspStatus;                     /* DSP's reply status */
 
1026
 
 
1027
    /* Make sure the DSP Id is valid. */
 
1028
    if (DspId >= MAX_DSP_CORES)
 
1029
        return (TfvInvalidDsp);
 
1030
 
 
1031
    /* Make sure the Channel Id is valid. */
 
1032
    if (ChannelId >= MaxChannels[DspId])
 
1033
        return (TfvInvalidChannel);
 
1034
 
 
1035
 
 
1036
    /* Build the message. */
 
1037
    MsgBuffer[0] = MSG_SERIAL_TXVAL << 8;
 
1038
    MsgBuffer[1] = (DSP_WORD) ((ChannelId << 8) | (State & 0xFF));
 
1039
    MsgBuffer[2] = (DSP_WORD) ((PcmOutPort << 8) | (PcmOutSlot & 0xFF));
 
1040
    MsgBuffer[3] = (DSP_WORD) Value;
 
1041
 
 
1042
    /* Attempt to send the message to the DSP and receive it's
 
1043
       reply. */
 
1044
    //need_reply_len;
 
1045
        if (!TransactCmd(DspId, MsgBuffer, 8, MSG_SERIAL_TXVAL_REPLY, 4,
 
1046
                                                            1, ChannelId))
 
1047
        return (TfvDspCommFailure);
 
1048
 
 
1049
    /* Return with an indication of success or failure based on the return
 
1050
       status in the reply message. */
 
1051
    DspStatus = (MsgBuffer[1] & 0xFF);
 
1052
    if (DspStatus == 0)
 
1053
        return (TfvSuccess);
 
1054
    else
 
1055
        return (TfvDspCommFailure);
 
1056
}
 
1057
 
 
1058
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 
1059
 * gpakControlTdmLoopBack - control a serial port's loopback state
 
1060
 * 
 
1061
 * FUNCTION
 
1062
 *  This function enables/disables the tdm input to output looback mode on a
 
1063
 *  serial port
 
1064
 * 
 
1065
 * RETURNS
 
1066
 *  Status  code indicating success or a specific error.
 
1067
 */
 
1068
 
 
1069
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -*/
 
1070
gpakControlTdmLoopBackStat_t gpakControlTdmLoopBack(
 
1071
    unsigned short int      DspId,          // DSP identifier
 
1072
    GpakSerialPort_t        SerialPort,     // Serial Port Id
 
1073
    GpakActivation          LoopBackState   // Loopback State
 
1074
    )
 
1075
{
 
1076
    DSP_WORD MsgBuffer[MSG_BUFFER_SIZE];    /* message buffer */
 
1077
    DSP_WORD DspStatus;                     /* DSP's reply status */
 
1078
 
 
1079
    /* Make sure the DSP Id is valid. */
 
1080
    if (DspId >= MAX_DSP_CORES)
 
1081
        return (ClbInvalidDsp);
 
1082
 
 
1083
    /* Build the message. */
 
1084
    MsgBuffer[0] = MSG_TDM_LOOPBACK << 8;
 
1085
    MsgBuffer[1] = (DSP_WORD) ((SerialPort << 8) | (LoopBackState & 0xFF));
 
1086
 
 
1087
    /* Attempt to send the message to the DSP and receive it's
 
1088
       reply. */
 
1089
    //need_reply_len;
 
1090
        if (!TransactCmd(DspId, MsgBuffer, 4, MSG_TDM_LOOPBACK_REPLY, 4, 0, 0))
 
1091
        return (ClbDspCommFailure);
 
1092
 
 
1093
    /* Return with an indication of success or failure based on the return
 
1094
       status in the reply message. */
 
1095
    DspStatus = (MsgBuffer[1] & 0xFF);
 
1096
    if (DspStatus == 0)
 
1097
        return (ClbSuccess);
 
1098
    else
 
1099
        return (ClbDspCommFailure);
 
1100
}
 
1101
 
 
1102
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 
1103
 * gpakReadCpuUsage - Read CPU usage statistics from a DSP.
 
1104
 *
 
1105
 * FUNCTION
 
1106
 *  This function reads the CPU usage statistics from a DSP's memory. The
 
1107
 *  average CPU usage in units of .1 percent are obtained for each of the frame
 
1108
 *  rates.
 
1109
 *
 
1110
 * RETURNS
 
1111
 *  Status code indicating success or a specific error.
 
1112
 *
 
1113
 */
 
1114
gpakReadCpuUsageStat_t gpakReadCpuUsage(
 
1115
    unsigned short int  DspId,              // Dsp Identifier
 
1116
    unsigned short int  *pPeakUsage,        // pointer to peak usage variable
 
1117
    unsigned short int  *pPrev1SecPeakUsage // peak usage over previous 1 second   
 
1118
    )
 
1119
{
 
1120
    DSP_WORD ReadBuffer[2];     /* DSP read buffer */
 
1121
 
 
1122
    /* Make sure the DSP Id is valid. */
 
1123
    if (DspId >= MAX_DSP_CORES)
 
1124
        return (RcuInvalidDsp);
 
1125
 
 
1126
    /* Lock access to the DSP. */
 
1127
    gpakLockAccess(DspId);
 
1128
 
 
1129
    /* Check if the DSP was reset and is ready. */
 
1130
    if (CheckDspReset(DspId) == -1)
 
1131
        return (RcuDspCommFailure);
 
1132
 
 
1133
    /* Read the CPU Usage statistics from the DSP. */
 
1134
    gpakReadDspMemory(DspId, pDspIfBlk[DspId] + CPU_USAGE_OFFSET, 2,
 
1135
                      ReadBuffer);
 
1136
 
 
1137
    /* Unlock access to the DSP. */
 
1138
    gpakUnlockAccess(DspId);
 
1139
 
 
1140
    /* Store the usage statistics in the specified variables. */
 
1141
    *pPrev1SecPeakUsage = ReadBuffer[0];
 
1142
    *pPeakUsage = ReadBuffer[1];
 
1143
    
 
1144
    /* Return with an indication the usage staistics were read successfully. */
 
1145
    return (RcuSuccess);
 
1146
}
 
1147
 
 
1148
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 
1149
 * gpakResetCpuUsageStats - reset the cpu usage statistics
 
1150
 * 
 
1151
 * FUNCTION
 
1152
 *  This function resets the cpu utilization statistics
 
1153
 * 
 
1154
 * RETURNS
 
1155
 *  Status  code indicating success or a specific error.
 
1156
 */
 
1157
gpakResetCpuUsageStat_t gpakResetCpuUsageStats(
 
1158
    unsigned short int  DspId              // DSP identifier
 
1159
    )
 
1160
{
 
1161
    DSP_WORD MsgBuffer[MSG_BUFFER_SIZE];    /* message buffer */
 
1162
    DSP_WORD DspStatus;                     /* DSP's reply status */
 
1163
 
 
1164
    /* Make sure the DSP Id is valid. */
 
1165
    if (DspId >= MAX_DSP_CORES)
 
1166
        return (RstcInvalidDsp);
 
1167
 
 
1168
    MsgBuffer[0] = (MSG_RESET_USAGE_STATS << 8);
 
1169
 
 
1170
    /* Attempt to send the message to the DSP and receive it's reply. */
 
1171
    //need_reply_len;
 
1172
        if (!TransactCmd(DspId, MsgBuffer, 2, MSG_RESET_USAGE_STATS_REPLY, 4, 0, 0))
 
1173
        return (RstcDspCommFailure);
 
1174
 
 
1175
    /* Return with an indication of success or failure based on the return
 
1176
       status in the reply message. */
 
1177
    DspStatus = (MsgBuffer[1] & 0xFF);
 
1178
    if (DspStatus == 0)
 
1179
        return (RstcSuccess);
 
1180
    else
 
1181
        return (RstcDspCommFailure);
 
1182
}
 
1183
 
 
1184
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 
1185
 * gpakReadFramingStats
 
1186
 * 
 
1187
 * FUNCTION
 
1188
 *  This function reads a DSP's framing interrupt statistics
 
1189
 * 
 
1190
 * RETURNS
 
1191
 *  Status  code indicating success or a specific error.
 
1192
 */
 
1193
gpakReadFramingStatsStatus_t gpakReadFramingStats(
 
1194
    unsigned short int  DspId,                // DSP identifier
 
1195
    unsigned short int  *pFramingError1Count, // port 1 Framing error count
 
1196
    unsigned short int  *pFramingError2Count, // port 2 Framing error count
 
1197
    unsigned short int  *pFramingError3Count, // port 3 Framing error count
 
1198
    unsigned short int  *pDmaStopErrorCount,   // DMA-stoppage error count
 
1199
    unsigned short int  *pDmaSlipStatsBuffer   // DMA slips count
 
1200
    )
 
1201
{
 
1202
    DSP_WORD ReadBuffer[10];     /* DSP read buffer */
 
1203
 
 
1204
    /* Make sure the DSP Id is valid. */
 
1205
    if (DspId >= MAX_DSP_CORES)
 
1206
        return (RfsInvalidDsp);
 
1207
 
 
1208
    /* Lock access to the DSP. */
 
1209
    gpakLockAccess(DspId);
 
1210
 
 
1211
    /* Check if the DSP was reset and is ready. */
 
1212
    if (CheckDspReset(DspId) == -1)
 
1213
        return (RfsDspCommFailure);
 
1214
 
 
1215
    /* Read the framing interrupt statistics from the DSP. */
 
1216
    gpakReadDspMemory(DspId, pDspIfBlk[DspId] + FRAMING_STATS_OFFSET, 10,
 
1217
                      ReadBuffer);
 
1218
 
 
1219
    /* Unlock access to the DSP. */
 
1220
    gpakUnlockAccess(DspId);
 
1221
 
 
1222
    /* Store the framing statistics in the specified variables. */
 
1223
    *pFramingError1Count = ReadBuffer[0];
 
1224
    *pFramingError2Count = ReadBuffer[1];
 
1225
    *pFramingError3Count = ReadBuffer[2];
 
1226
    *pDmaStopErrorCount  = ReadBuffer[3];
 
1227
    
 
1228
    if(pDmaSlipStatsBuffer != 0) 
 
1229
    // If users want to get the DMA slips count
 
1230
    {
 
1231
            pDmaSlipStatsBuffer[0] = ReadBuffer[4];
 
1232
        pDmaSlipStatsBuffer[1] = ReadBuffer[5];
 
1233
        pDmaSlipStatsBuffer[2] = ReadBuffer[6];
 
1234
        pDmaSlipStatsBuffer[3] = ReadBuffer[7];
 
1235
        pDmaSlipStatsBuffer[4] = ReadBuffer[8];
 
1236
        pDmaSlipStatsBuffer[5] = ReadBuffer[9];
 
1237
    
 
1238
    }
 
1239
    /* Return with an indication the statistics were read successfully. */
 
1240
    return (RfsSuccess);
 
1241
}
 
1242
 
 
1243
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 
1244
 * gpakResetFramingStats - reset a DSP's framing interrupt statistics
 
1245
 * 
 
1246
 * FUNCTION
 
1247
 *  This function resets a DSP's framing interrupt statistics
 
1248
 * 
 
1249
 * RETURNS
 
1250
 *  Status  code indicating success or a specific error.
 
1251
 */
 
1252
gpakResetFramingStatsStatus_t gpakResetFramingStats(
 
1253
    unsigned short int      DspId          // DSP identifier
 
1254
    )
 
1255
{
 
1256
    DSP_WORD MsgBuffer[MSG_BUFFER_SIZE];    /* message buffer */
 
1257
    DSP_WORD DspStatus;                     /* DSP's reply status */
 
1258
 
 
1259
    /* Make sure the DSP Id is valid. */
 
1260
    if (DspId >= MAX_DSP_CORES)
 
1261
        return (RstfInvalidDsp);
 
1262
 
 
1263
    MsgBuffer[0] = (MSG_RESET_FRAME_STATS << 8);
 
1264
 
 
1265
    /* Attempt to send the message to the DSP and receive it's reply. */
 
1266
    //need_reply_len;
 
1267
        if (!TransactCmd(DspId, MsgBuffer, 2, MSG_RESET_FRAME_STATS_REPLY, 4, 0, 0))
 
1268
        return (RstfDspCommFailure);
 
1269
 
 
1270
    /* Return with an indication of success or failure based on the return
 
1271
       status in the reply message. */
 
1272
    DspStatus = (MsgBuffer[1] & 0xFF);
 
1273
    if (DspStatus == 0)
 
1274
        return (RstfSuccess);
 
1275
    else
 
1276
        return (RstfDspCommFailure);
 
1277
}
 
1278
 
 
1279
/*
 
1280
 * gpakDownloadDsp - Download a DSP's Program and initialized Data memory.
 
1281
 *
 
1282
 * FUNCTION
 
1283
 *  This function reads a DSP's Program and Data memory image from the
 
1284
 *  specified file and writes the image to the DSP's memory.
 
1285
 *
 
1286
 * RETURNS
 
1287
 *  Status code indicating success or a specific error.
 
1288
 *
 
1289
 */
 
1290
gpakDownloadStatus_t gpakDownloadDsp(
 
1291
    unsigned short DspId,   /* DSP Identifier (0 to MaxDSPCores-1) */
 
1292
    GPAK_FILE_ID FileId     /* G.PAK Download File Identifier */
 
1293
    )
 
1294
{
 
1295
    gpakDownloadStatus_t RetStatus;     /* function return status */
 
1296
    int NumRead;                        /* number of file bytes read */
 
1297
    DSP_ADDRESS Address;                /* DSP address */
 
1298
    unsigned int WordCount;             /* number of words in record */
 
1299
    unsigned int NumWords;              /* number of words to read/write */
 
1300
    unsigned int i;                     /* loop index / counter */
 
1301
    unsigned int j;                     /* loop index */
 
1302
 
 
1303
    /* Make sure the DSP Id is valid. */
 
1304
    if (DspId >= MAX_DSP_CORES)
 
1305
        return (GdlInvalidDsp);
 
1306
 
 
1307
    /* Lock access to the DSP. */
 
1308
    gpakLockAccess(DspId);
 
1309
 
 
1310
    RetStatus = GdlSuccess;
 
1311
    while (RetStatus == GdlSuccess)
 
1312
    {
 
1313
 
 
1314
        /* Read a record header from the file. */
 
1315
        NumRead = gpakReadFile(FileId, DlByteBufr, 6);
 
1316
        if (NumRead == -1)
 
1317
        {
 
1318
            RetStatus = GdlFileReadError;
 
1319
            break;
 
1320
        }
 
1321
        if (NumRead != 6)
 
1322
        {
 
1323
            RetStatus = GdlInvalidFile;
 
1324
            break;
 
1325
        }
 
1326
        Address = (((DSP_ADDRESS) DlByteBufr[1]) << 16) |
 
1327
                  (((DSP_ADDRESS) DlByteBufr[2]) << 8) |
 
1328
                  ((DSP_ADDRESS) DlByteBufr[3]);
 
1329
        WordCount = (((unsigned int) DlByteBufr[4]) << 8) |
 
1330
                    ((unsigned int) DlByteBufr[5]);
 
1331
 
 
1332
        /* Check for the End Of File record. */
 
1333
        if (DlByteBufr[0] == 0xFF)
 
1334
            break;
 
1335
 
 
1336
        /* Verify the record is for a valid memory type. */
 
1337
        if ((DlByteBufr[0] != 0x00) && (DlByteBufr[0] != 0x01))
 
1338
        {
 
1339
            RetStatus = GdlInvalidFile;
 
1340
            break;
 
1341
        }
 
1342
 
 
1343
        /* Read a block of words at a time from the file and write to the
 
1344
           DSP's memory .*/
 
1345
        while (WordCount != 0)
 
1346
        {
 
1347
            if (WordCount < DOWNLOAD_BLOCK_SIZE)
 
1348
                NumWords = WordCount;
 
1349
            else
 
1350
                NumWords = DOWNLOAD_BLOCK_SIZE;
 
1351
            WordCount -= NumWords;
 
1352
            NumRead = gpakReadFile(FileId, DlByteBufr, NumWords * 2);
 
1353
            if (NumRead == -1)
 
1354
            {
 
1355
                RetStatus = GdlFileReadError;
 
1356
                break;
 
1357
            }
 
1358
            if (NumRead != (NumWords * 2))
 
1359
            {
 
1360
                RetStatus = GdlInvalidFile;
 
1361
                break;
 
1362
            }
 
1363
            for (i = 0, j = 0; i < NumWords; i++, j += 2)
 
1364
                DlWordBufr[i] = (((DSP_WORD) DlByteBufr[j]) << 8) |
 
1365
                                ((DSP_WORD) DlByteBufr[j + 1]);
 
1366
            gpakWriteDspMemory(DspId, Address, NumWords, DlWordBufr);
 
1367
            Address += ((DSP_ADDRESS) NumWords);
 
1368
        }
 
1369
    }
 
1370
 
 
1371
    /* Unlock access to the DSP. */
 
1372
    gpakUnlockAccess(DspId);
 
1373
 
 
1374
    /* Return with an indication of success or failure. */
 
1375
    return (RetStatus);
 
1376
}
 
1377
 
 
1378
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 
1379
 * gpakReadCpuUsage - Read CPU usage statistics from a DSP.
 
1380
 *
 
1381
 * FUNCTION
 
1382
 *  This function reads the memory map register section of DSP memory. 
 
1383
 *
 
1384
 * RETURNS
 
1385
 *  Status code indicating success or a specific error.
 
1386
 *
 
1387
 */
 
1388
gpakReadDSPMemoryStat_t gpakReadDSPMemoryMap(
 
1389
    unsigned short int  DspId,         // Dsp Identifier
 
1390
    unsigned short int  *pDest,        // Buffer on host to hold DSP memory map
 
1391
        DSP_ADDRESS BufrBaseAddress,       // DSP memory users want to read out
 
1392
    unsigned short int   MemoryLength_Word16 // Length of memory section read out, unit is 16-bit word
 
1393
    )
 
1394
{
 
1395
    DSP_WORD MsgBuffer[MSG_BUFFER_SIZE];    /* message buffer */
 
1396
    DSP_WORD DspStatus;                     /* DSP reply's status */
 
1397
    int i;                                  /* loop index / counter */
 
1398
 
 
1399
    
 
1400
    /* Make sure the DSP Id is valid. */
 
1401
    if (DspId >= MAX_DSP_CORES)
 
1402
        return (RmmInvalidDsp);
 
1403
 
 
1404
    /* Verify the message buffer is large enough  */
 
1405
    if (MSG_BUFFER_SIZE < MemoryLength_Word16 )
 
1406
        return (RmmSizeTooBig);
 
1407
 
 
1408
    MsgBuffer[0] = MSG_READ_DSP_MEMORY << 8;
 
1409
    MsgBuffer[1] = (DSP_WORD) ((BufrBaseAddress >> 16) & 0xFFFF);
 
1410
    MsgBuffer[2] = (DSP_WORD) (BufrBaseAddress & 0xFFFF);
 
1411
    MsgBuffer[3] = (DSP_WORD) MemoryLength_Word16;
 
1412
 
 
1413
    /* Attempt to send the Read memory section message to the DSP and receive it's
 
1414
       reply. */
 
1415
        //need_reply_len;       
 
1416
        if (!TransactCmd(DspId, MsgBuffer, 8, MSG_READ_DSP_MEMORY_REPLY, 
 
1417
                        (MemoryLength_Word16+2)*2, 0,  0) )
 
1418
        return (RmmInvalidAddress);
 
1419
 
 
1420
    /* Return with an indication of success or failure based on the return
 
1421
       status in the reply message. */
 
1422
    DspStatus = (MsgBuffer[1] & 0xFF);
 
1423
    if (DspStatus != 0)
 
1424
        return (RmmFailure);
 
1425
 
 
1426
        for (i = 0; i < MemoryLength_Word16; i++)
 
1427
        pDest[i] = (short int) MsgBuffer[2 + i];
 
1428
 
 
1429
 
 
1430
    return (RmmSuccess);
 
1431
}
 
1432
 
 
1433
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 
1434
 * gpakAccessGPIO - change Direction/read/write the GPIO on DSP 
 
1435
 * 
 
1436
 * FUNCTION
 
1437
 *  This function read/write GPIO and change the GPIO direction
 
1438
 *  
 
1439
 * 
 
1440
 * RETURNS
 
1441
 *  Status  code indicating success or a specific error.
 
1442
 */
 
1443
gpakAccessGPIOStat_t gpakAccessGPIO(
 
1444
    unsigned short int      DspId,          // DSP identifier
 
1445
        GpakGPIOCotrol_t        gpakControlGPIO,// select oeration, changeDIR/write/read
 
1446
    unsigned short int      *pGPIOValue  // DSP software version
 
1447
    )
 
1448
{
 
1449
    DSP_WORD MsgBuffer[MSG_BUFFER_SIZE];    /* message buffer */
 
1450
    DSP_WORD DspStatus;                     /* DSP's reply status */
 
1451
 
 
1452
    /* Make sure the DSP Id is valid. */
 
1453
    if (DspId >= MAX_DSP_CORES)
 
1454
        return (GPIOInvalidDsp);
 
1455
 
 
1456
    /* send value of 1, DSP increments it */
 
1457
    MsgBuffer[0] = (MSG_ACCESSGPIO << 8);
 
1458
        MsgBuffer[1] = (DSP_WORD) ((gpakControlGPIO << 8) | (*pGPIOValue & 0xFF) );
 
1459
    /* Attempt to send the ping message to the DSP and receive it's
 
1460
       reply. */
 
1461
        if (!TransactCmd(DspId, MsgBuffer, 4, MSG_ACCESSGPIO_REPLY, 6, 0, 0))
 
1462
        return (GPIODspCommFailure);
 
1463
 
 
1464
    /* Return with an indication of success or failure based on the return
 
1465
       status in the reply message. */
 
1466
    DspStatus = (MsgBuffer[1] & 0xFF);
 
1467
    if (DspStatus == 0)
 
1468
    {
 
1469
        *pGPIOValue = MsgBuffer[2];
 
1470
        return (GPIOSuccess);
 
1471
    }
 
1472
    else
 
1473
        return (GPIODspCommFailure);
 
1474
}
 
1475
 
 
1476
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 
1477
 * gpakWriteSystemParms - Write a DSP's System Parameters.
 
1478
 *
 
1479
 * FUNCTION
 
1480
 *  This function writes a DSP's System Parameters information.
 
1481
 *
 
1482
 *    Note:
 
1483
 *      Or-together the desired bit-mask #defines that are listed below. Only
 
1484
 *      those algorithm parameters whose bit-mask is selected in the UpdateBits
 
1485
 *      function parameter will be updated.
 
1486
 *
 
1487
 * RETURNS
 
1488
 *  Status code indicating success or a specific error.
 
1489
 *
 
1490
 */
 
1491
 
 
1492
gpakWriteSysParmsStatus_t gpakWriteSystemParms(
 
1493
    unsigned short int      DspId,  // DSP identifier
 
1494
    GpakSystemParms_t *pSysParms,   /* pointer to System Parms info var */
 
1495
    unsigned short int UpdateBits, /* input: flags indicating which parms to update */
 
1496
    GPAK_SysParmsStat_t *pStatus    /* pointer to Write System Parms Status */
 
1497
    )
 
1498
{
 
1499
    DSP_WORD MsgBuffer[MSG_BUFFER_SIZE];    /* message buffer */
 
1500
    DSP_WORD DspStatus;                     /* DSP's reply status */
 
1501
 
 
1502
    /* Make sure the DSP Id is valid. */
 
1503
    if (DspId >= MAX_DSP_CORES)
 
1504
        return (WspInvalidDsp);
 
1505
 
 
1506
    /* Build the Write System Parameters message. */
 
1507
    MsgBuffer[0] = MSG_WRITE_SYS_PARMS << 8;
 
1508
 
 
1509
    if (UpdateBits & DTMF_UPDATE_MASK)
 
1510
    {
 
1511
        MsgBuffer[1] |= DTMF_UPDATE_MASK;
 
1512
        MsgBuffer[8] = (DSP_WORD) pSysParms->MinSigLevel;
 
1513
        MsgBuffer[9] = (DSP_WORD) (pSysParms->FreqDeviation & 0xff);
 
1514
        if (pSysParms->SNRFlag)
 
1515
            MsgBuffer[9] |= (1<<8);
 
1516
    }
 
1517
 
 
1518
    MsgBuffer[10] = (DSP_WORD) 0;
 
1519
    if (UpdateBits & DTMF_TWIST_UPDATE_MASK)
 
1520
    {
 
1521
        MsgBuffer[1] |= DTMF_TWIST_UPDATE_MASK;
 
1522
        MsgBuffer[10] |= (DSP_WORD) (pSysParms->DtmfFwdTwist & 0x000f);
 
1523
        MsgBuffer[10] |= (DSP_WORD) ((pSysParms->DtmfRevTwist << 4) & 0x00f0);
 
1524
    }
 
1525
 
 
1526
 
 
1527
    if (UpdateBits & DTMF_VALID_MASK)
 
1528
    {
 
1529
        MsgBuffer[1] |= DTMF_VALID_MASK;
 
1530
            MsgBuffer[11] = (DSP_WORD) (pSysParms->DtmfValidityMask & 0x00ff);
 
1531
        }
 
1532
 
 
1533
    /* Attempt to send the ping message to the DSP and receive it's
 
1534
       reply. */
 
1535
        if (!TransactCmd(DspId, MsgBuffer, 24, MSG_WRITE_SYS_PARMS_REPLY, 6, 0, 0))
 
1536
        return (WspDspCommFailure);
 
1537
 
 
1538
    /* Return with an indication of success or failure based on the return
 
1539
       status in the reply message. */
 
1540
    *pStatus = (GPAK_SysParmsStat_t) (MsgBuffer[2] );
 
1541
 
 
1542
    DspStatus = (MsgBuffer[1] & 0xFF);
 
1543
    if (DspStatus == 0)
 
1544
        return (WspSuccess);
 
1545
    else
 
1546
        return (WspDspCommFailure);
 
1547
}
 
1548
 
 
1549
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 
1550
 * gpakReadSystemParms - Read a DSP's System Parameters.
 
1551
 *
 
1552
 * FUNCTION
 
1553
 *  This function reads a DSP's System Parameters information.
 
1554
 *
 
1555
 * RETURNS
 
1556
 *  Status code indicating success or a specific error.
 
1557
 *
 
1558
 */
 
1559
gpakReadSysParmsStatus_t gpakReadSystemParms(
 
1560
    unsigned short int      DspId,  // DSP identifier
 
1561
    GpakSystemParms_t *pSysParms    /* pointer to System Parms info var */
 
1562
    )
 
1563
{
 
1564
 
 
1565
    DSP_WORD MsgBuffer[MSG_BUFFER_SIZE];    /* message buffer */
 
1566
 
 
1567
    /* Make sure the DSP Id is valid. */
 
1568
    if (DspId >= MAX_DSP_CORES)
 
1569
        return (RspInvalidDsp);
 
1570
 
 
1571
    /* Build the Read System Parameters message. */
 
1572
    MsgBuffer[0] = MSG_READ_SYS_PARMS << 8;
 
1573
 
 
1574
    /* Attempt to send the ping message to the DSP and receive it's
 
1575
       reply. */
 
1576
        if (!TransactCmd(DspId, MsgBuffer, 2, MSG_READ_SYS_PARMS_REPLY, 22, 0, 0))
 
1577
        return (RspDspCommFailure);
 
1578
 
 
1579
    /* Extract the System Parameters information from the message. */
 
1580
    pSysParms->DtmfValidityMask = (short int)(MsgBuffer[7]) ;
 
1581
 
 
1582
    pSysParms->MinSigLevel   =  (short int)MsgBuffer[8];
 
1583
    pSysParms->SNRFlag       = (short int)((MsgBuffer[9]>>8) & 0x1);
 
1584
    pSysParms->FreqDeviation =  (short int)(MsgBuffer[9] & 0xff);
 
1585
    pSysParms->DtmfFwdTwist  = (short int)MsgBuffer[10] & 0x000f;
 
1586
    pSysParms->DtmfRevTwist  = (short int)(MsgBuffer[10] >> 4) & 0x000f;
 
1587
 
 
1588
    /* Return with an indication that System Parameters info was obtained. */
 
1589
    return (RspSuccess);
 
1590
}