Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
torvalds
GitHub Repository: torvalds/linux
Path: blob/master/sound/pci/asihpi/hpi6205.c
26439 views
1
// SPDX-License-Identifier: GPL-2.0-only
2
/******************************************************************************
3
4
AudioScience HPI driver
5
Copyright (C) 1997-2014 AudioScience Inc. <[email protected]>
6
7
8
Hardware Programming Interface (HPI) for AudioScience
9
ASI50xx, AS51xx, ASI6xxx, ASI87xx ASI89xx series adapters.
10
These PCI and PCIe bus adapters are based on a
11
TMS320C6205 PCI bus mastering DSP,
12
and (except ASI50xx) TI TMS320C6xxx floating point DSP
13
14
Exported function:
15
void HPI_6205(struct hpi_message *phm, struct hpi_response *phr)
16
17
(C) Copyright AudioScience Inc. 1998-2010
18
*******************************************************************************/
19
#define SOURCEFILE_NAME "hpi6205.c"
20
21
#include "hpi_internal.h"
22
#include "hpimsginit.h"
23
#include "hpidebug.h"
24
#include "hpi6205.h"
25
#include "hpidspcd.h"
26
#include "hpicmn.h"
27
28
/*****************************************************************************/
29
/* HPI6205 specific error codes */
30
#define HPI6205_ERROR_BASE 1000 /* not actually used anywhere */
31
32
/* operational/messaging errors */
33
#define HPI6205_ERROR_MSG_RESP_IDLE_TIMEOUT 1015
34
#define HPI6205_ERROR_MSG_RESP_TIMEOUT 1016
35
36
/* initialization/bootload errors */
37
#define HPI6205_ERROR_6205_NO_IRQ 1002
38
#define HPI6205_ERROR_6205_INIT_FAILED 1003
39
#define HPI6205_ERROR_6205_REG 1006
40
#define HPI6205_ERROR_6205_DSPPAGE 1007
41
#define HPI6205_ERROR_C6713_HPIC 1009
42
#define HPI6205_ERROR_C6713_HPIA 1010
43
#define HPI6205_ERROR_C6713_PLL 1011
44
#define HPI6205_ERROR_DSP_INTMEM 1012
45
#define HPI6205_ERROR_DSP_EXTMEM 1013
46
#define HPI6205_ERROR_DSP_PLD 1014
47
#define HPI6205_ERROR_6205_EEPROM 1017
48
#define HPI6205_ERROR_DSP_EMIF1 1018
49
#define HPI6205_ERROR_DSP_EMIF2 1019
50
#define HPI6205_ERROR_DSP_EMIF3 1020
51
#define HPI6205_ERROR_DSP_EMIF4 1021
52
53
/*****************************************************************************/
54
/* for C6205 PCI i/f */
55
/* Host Status Register (HSR) bitfields */
56
#define C6205_HSR_INTSRC 0x01
57
#define C6205_HSR_INTAVAL 0x02
58
#define C6205_HSR_INTAM 0x04
59
#define C6205_HSR_CFGERR 0x08
60
#define C6205_HSR_EEREAD 0x10
61
/* Host-to-DSP Control Register (HDCR) bitfields */
62
#define C6205_HDCR_WARMRESET 0x01
63
#define C6205_HDCR_DSPINT 0x02
64
#define C6205_HDCR_PCIBOOT 0x04
65
/* DSP Page Register (DSPP) bitfields, */
66
/* defines 4 Mbyte page that BAR0 points to */
67
#define C6205_DSPP_MAP1 0x400
68
69
/* BAR0 maps to prefetchable 4 Mbyte memory block set by DSPP.
70
* BAR1 maps to non-prefetchable 8 Mbyte memory block
71
* of DSP memory mapped registers (starting at 0x01800000).
72
* 0x01800000 is hardcoded in the PCI i/f, so that only the offset from this
73
* needs to be added to the BAR1 base address set in the PCI config reg
74
*/
75
#define C6205_BAR1_PCI_IO_OFFSET (0x027FFF0L)
76
#define C6205_BAR1_HSR (C6205_BAR1_PCI_IO_OFFSET)
77
#define C6205_BAR1_HDCR (C6205_BAR1_PCI_IO_OFFSET+4)
78
#define C6205_BAR1_DSPP (C6205_BAR1_PCI_IO_OFFSET+8)
79
80
/* used to control LED (revA) and reset C6713 (revB) */
81
#define C6205_BAR0_TIMER1_CTL (0x01980000L)
82
83
/* For first 6713 in CE1 space, using DA17,16,2 */
84
#define HPICL_ADDR 0x01400000L
85
#define HPICH_ADDR 0x01400004L
86
#define HPIAL_ADDR 0x01410000L
87
#define HPIAH_ADDR 0x01410004L
88
#define HPIDIL_ADDR 0x01420000L
89
#define HPIDIH_ADDR 0x01420004L
90
#define HPIDL_ADDR 0x01430000L
91
#define HPIDH_ADDR 0x01430004L
92
93
#define C6713_EMIF_GCTL 0x01800000
94
#define C6713_EMIF_CE1 0x01800004
95
#define C6713_EMIF_CE0 0x01800008
96
#define C6713_EMIF_CE2 0x01800010
97
#define C6713_EMIF_CE3 0x01800014
98
#define C6713_EMIF_SDRAMCTL 0x01800018
99
#define C6713_EMIF_SDRAMTIMING 0x0180001C
100
#define C6713_EMIF_SDRAMEXT 0x01800020
101
102
struct hpi_hw_obj {
103
/* PCI registers */
104
__iomem u32 *prHSR;
105
__iomem u32 *prHDCR;
106
__iomem u32 *prDSPP;
107
108
u32 dsp_page;
109
110
struct consistent_dma_area h_locked_mem;
111
struct bus_master_interface *p_interface_buffer;
112
113
u16 flag_outstream_just_reset[HPI_MAX_STREAMS];
114
/* a non-NULL handle means there is an HPI allocated buffer */
115
struct consistent_dma_area instream_host_buffers[HPI_MAX_STREAMS];
116
struct consistent_dma_area outstream_host_buffers[HPI_MAX_STREAMS];
117
/* non-zero size means a buffer exists, may be external */
118
u32 instream_host_buffer_size[HPI_MAX_STREAMS];
119
u32 outstream_host_buffer_size[HPI_MAX_STREAMS];
120
121
struct consistent_dma_area h_control_cache;
122
struct hpi_control_cache *p_cache;
123
};
124
125
/*****************************************************************************/
126
/* local prototypes */
127
128
#define check_before_bbm_copy(status, p_bbm_data, l_first_write, l_second_write)
129
130
static int wait_dsp_ack(struct hpi_hw_obj *phw, int state, int timeout_us);
131
132
static void send_dsp_command(struct hpi_hw_obj *phw, int cmd);
133
134
static u16 adapter_boot_load_dsp(struct hpi_adapter_obj *pao,
135
u32 *pos_error_code);
136
137
static u16 message_response_sequence(struct hpi_adapter_obj *pao,
138
struct hpi_message *phm, struct hpi_response *phr);
139
140
static void hw_message(struct hpi_adapter_obj *pao, struct hpi_message *phm,
141
struct hpi_response *phr);
142
143
#define HPI6205_TIMEOUT 1000000
144
145
static void subsys_create_adapter(struct hpi_message *phm,
146
struct hpi_response *phr);
147
static void adapter_delete(struct hpi_adapter_obj *pao,
148
struct hpi_message *phm, struct hpi_response *phr);
149
150
static u16 create_adapter_obj(struct hpi_adapter_obj *pao,
151
u32 *pos_error_code);
152
153
static void delete_adapter_obj(struct hpi_adapter_obj *pao);
154
155
static int adapter_irq_query_and_clear(struct hpi_adapter_obj *pao,
156
u32 message);
157
158
static void outstream_host_buffer_allocate(struct hpi_adapter_obj *pao,
159
struct hpi_message *phm, struct hpi_response *phr);
160
161
static void outstream_host_buffer_get_info(struct hpi_adapter_obj *pao,
162
struct hpi_message *phm, struct hpi_response *phr);
163
164
static void outstream_host_buffer_free(struct hpi_adapter_obj *pao,
165
struct hpi_message *phm, struct hpi_response *phr);
166
static void outstream_write(struct hpi_adapter_obj *pao,
167
struct hpi_message *phm, struct hpi_response *phr);
168
169
static void outstream_get_info(struct hpi_adapter_obj *pao,
170
struct hpi_message *phm, struct hpi_response *phr);
171
172
static void outstream_start(struct hpi_adapter_obj *pao,
173
struct hpi_message *phm, struct hpi_response *phr);
174
175
static void outstream_open(struct hpi_adapter_obj *pao,
176
struct hpi_message *phm, struct hpi_response *phr);
177
178
static void outstream_reset(struct hpi_adapter_obj *pao,
179
struct hpi_message *phm, struct hpi_response *phr);
180
181
static void instream_host_buffer_allocate(struct hpi_adapter_obj *pao,
182
struct hpi_message *phm, struct hpi_response *phr);
183
184
static void instream_host_buffer_get_info(struct hpi_adapter_obj *pao,
185
struct hpi_message *phm, struct hpi_response *phr);
186
187
static void instream_host_buffer_free(struct hpi_adapter_obj *pao,
188
struct hpi_message *phm, struct hpi_response *phr);
189
190
static void instream_read(struct hpi_adapter_obj *pao,
191
struct hpi_message *phm, struct hpi_response *phr);
192
193
static void instream_get_info(struct hpi_adapter_obj *pao,
194
struct hpi_message *phm, struct hpi_response *phr);
195
196
static void instream_start(struct hpi_adapter_obj *pao,
197
struct hpi_message *phm, struct hpi_response *phr);
198
199
static u32 boot_loader_read_mem32(struct hpi_adapter_obj *pao, int dsp_index,
200
u32 address);
201
202
static void boot_loader_write_mem32(struct hpi_adapter_obj *pao,
203
int dsp_index, u32 address, u32 data);
204
205
static u16 boot_loader_config_emif(struct hpi_adapter_obj *pao,
206
int dsp_index);
207
208
static u16 boot_loader_test_memory(struct hpi_adapter_obj *pao, int dsp_index,
209
u32 address, u32 length);
210
211
static u16 boot_loader_test_internal_memory(struct hpi_adapter_obj *pao,
212
int dsp_index);
213
214
static u16 boot_loader_test_external_memory(struct hpi_adapter_obj *pao,
215
int dsp_index);
216
217
static u16 boot_loader_test_pld(struct hpi_adapter_obj *pao, int dsp_index);
218
219
/*****************************************************************************/
220
221
static void subsys_message(struct hpi_adapter_obj *pao,
222
struct hpi_message *phm, struct hpi_response *phr)
223
{
224
switch (phm->function) {
225
case HPI_SUBSYS_CREATE_ADAPTER:
226
subsys_create_adapter(phm, phr);
227
break;
228
default:
229
phr->error = HPI_ERROR_INVALID_FUNC;
230
break;
231
}
232
}
233
234
static void control_message(struct hpi_adapter_obj *pao,
235
struct hpi_message *phm, struct hpi_response *phr)
236
{
237
238
struct hpi_hw_obj *phw = pao->priv;
239
u16 pending_cache_error = 0;
240
241
switch (phm->function) {
242
case HPI_CONTROL_GET_STATE:
243
if (pao->has_control_cache) {
244
rmb(); /* make sure we see updates DMAed from DSP */
245
if (hpi_check_control_cache(phw->p_cache, phm, phr)) {
246
break;
247
} else if (phm->u.c.attribute == HPI_METER_PEAK) {
248
pending_cache_error =
249
HPI_ERROR_CONTROL_CACHING;
250
}
251
}
252
hw_message(pao, phm, phr);
253
if (pending_cache_error && !phr->error)
254
phr->error = pending_cache_error;
255
break;
256
case HPI_CONTROL_GET_INFO:
257
hw_message(pao, phm, phr);
258
break;
259
case HPI_CONTROL_SET_STATE:
260
hw_message(pao, phm, phr);
261
if (pao->has_control_cache)
262
hpi_cmn_control_cache_sync_to_msg(phw->p_cache, phm,
263
phr);
264
break;
265
default:
266
phr->error = HPI_ERROR_INVALID_FUNC;
267
break;
268
}
269
}
270
271
static void adapter_message(struct hpi_adapter_obj *pao,
272
struct hpi_message *phm, struct hpi_response *phr)
273
{
274
switch (phm->function) {
275
case HPI_ADAPTER_DELETE:
276
adapter_delete(pao, phm, phr);
277
break;
278
default:
279
hw_message(pao, phm, phr);
280
break;
281
}
282
}
283
284
static void outstream_message(struct hpi_adapter_obj *pao,
285
struct hpi_message *phm, struct hpi_response *phr)
286
{
287
288
if (phm->obj_index >= HPI_MAX_STREAMS) {
289
phr->error = HPI_ERROR_INVALID_OBJ_INDEX;
290
HPI_DEBUG_LOG(WARNING,
291
"Message referencing invalid stream %d "
292
"on adapter index %d\n", phm->obj_index,
293
phm->adapter_index);
294
return;
295
}
296
297
switch (phm->function) {
298
case HPI_OSTREAM_WRITE:
299
outstream_write(pao, phm, phr);
300
break;
301
case HPI_OSTREAM_GET_INFO:
302
outstream_get_info(pao, phm, phr);
303
break;
304
case HPI_OSTREAM_HOSTBUFFER_ALLOC:
305
outstream_host_buffer_allocate(pao, phm, phr);
306
break;
307
case HPI_OSTREAM_HOSTBUFFER_GET_INFO:
308
outstream_host_buffer_get_info(pao, phm, phr);
309
break;
310
case HPI_OSTREAM_HOSTBUFFER_FREE:
311
outstream_host_buffer_free(pao, phm, phr);
312
break;
313
case HPI_OSTREAM_START:
314
outstream_start(pao, phm, phr);
315
break;
316
case HPI_OSTREAM_OPEN:
317
outstream_open(pao, phm, phr);
318
break;
319
case HPI_OSTREAM_RESET:
320
outstream_reset(pao, phm, phr);
321
break;
322
default:
323
hw_message(pao, phm, phr);
324
break;
325
}
326
}
327
328
static void instream_message(struct hpi_adapter_obj *pao,
329
struct hpi_message *phm, struct hpi_response *phr)
330
{
331
332
if (phm->obj_index >= HPI_MAX_STREAMS) {
333
phr->error = HPI_ERROR_INVALID_OBJ_INDEX;
334
HPI_DEBUG_LOG(WARNING,
335
"Message referencing invalid stream %d "
336
"on adapter index %d\n", phm->obj_index,
337
phm->adapter_index);
338
return;
339
}
340
341
switch (phm->function) {
342
case HPI_ISTREAM_READ:
343
instream_read(pao, phm, phr);
344
break;
345
case HPI_ISTREAM_GET_INFO:
346
instream_get_info(pao, phm, phr);
347
break;
348
case HPI_ISTREAM_HOSTBUFFER_ALLOC:
349
instream_host_buffer_allocate(pao, phm, phr);
350
break;
351
case HPI_ISTREAM_HOSTBUFFER_GET_INFO:
352
instream_host_buffer_get_info(pao, phm, phr);
353
break;
354
case HPI_ISTREAM_HOSTBUFFER_FREE:
355
instream_host_buffer_free(pao, phm, phr);
356
break;
357
case HPI_ISTREAM_START:
358
instream_start(pao, phm, phr);
359
break;
360
default:
361
hw_message(pao, phm, phr);
362
break;
363
}
364
}
365
366
/*****************************************************************************/
367
/** Entry point to this HPI backend
368
* All calls to the HPI start here
369
*/
370
static
371
void _HPI_6205(struct hpi_adapter_obj *pao, struct hpi_message *phm,
372
struct hpi_response *phr)
373
{
374
if (pao && (pao->dsp_crashed >= 10)
375
&& (phm->function != HPI_ADAPTER_DEBUG_READ)) {
376
/* allow last resort debug read even after crash */
377
hpi_init_response(phr, phm->object, phm->function,
378
HPI_ERROR_DSP_HARDWARE);
379
HPI_DEBUG_LOG(WARNING, " %d,%d dsp crashed.\n", phm->object,
380
phm->function);
381
return;
382
}
383
384
/* Init default response */
385
if (phm->function != HPI_SUBSYS_CREATE_ADAPTER)
386
phr->error = HPI_ERROR_PROCESSING_MESSAGE;
387
388
HPI_DEBUG_LOG(VERBOSE, "start of switch\n");
389
switch (phm->type) {
390
case HPI_TYPE_REQUEST:
391
switch (phm->object) {
392
case HPI_OBJ_SUBSYSTEM:
393
subsys_message(pao, phm, phr);
394
break;
395
396
case HPI_OBJ_ADAPTER:
397
adapter_message(pao, phm, phr);
398
break;
399
400
case HPI_OBJ_CONTROL:
401
control_message(pao, phm, phr);
402
break;
403
404
case HPI_OBJ_OSTREAM:
405
outstream_message(pao, phm, phr);
406
break;
407
408
case HPI_OBJ_ISTREAM:
409
instream_message(pao, phm, phr);
410
break;
411
412
default:
413
hw_message(pao, phm, phr);
414
break;
415
}
416
break;
417
418
default:
419
phr->error = HPI_ERROR_INVALID_TYPE;
420
break;
421
}
422
}
423
424
void HPI_6205(struct hpi_message *phm, struct hpi_response *phr)
425
{
426
struct hpi_adapter_obj *pao = NULL;
427
428
if (phm->object != HPI_OBJ_SUBSYSTEM) {
429
/* normal messages must have valid adapter index */
430
pao = hpi_find_adapter(phm->adapter_index);
431
} else {
432
/* subsys messages don't address an adapter */
433
phr->error = HPI_ERROR_INVALID_OBJ_INDEX;
434
return;
435
}
436
437
if (pao)
438
_HPI_6205(pao, phm, phr);
439
else
440
hpi_init_response(phr, phm->object, phm->function,
441
HPI_ERROR_BAD_ADAPTER_NUMBER);
442
}
443
444
/*****************************************************************************/
445
/* SUBSYSTEM */
446
447
/** Create an adapter object and initialise it based on resource information
448
* passed in the message
449
* *** NOTE - you cannot use this function AND the FindAdapters function at the
450
* same time, the application must use only one of them to get the adapters ***
451
*/
452
static void subsys_create_adapter(struct hpi_message *phm,
453
struct hpi_response *phr)
454
{
455
/* create temp adapter obj, because we don't know what index yet */
456
struct hpi_adapter_obj ao;
457
u32 os_error_code;
458
u16 err;
459
460
HPI_DEBUG_LOG(DEBUG, " subsys_create_adapter\n");
461
462
memset(&ao, 0, sizeof(ao));
463
464
ao.priv = kzalloc(sizeof(struct hpi_hw_obj), GFP_KERNEL);
465
if (!ao.priv) {
466
HPI_DEBUG_LOG(ERROR, "can't get mem for adapter object\n");
467
phr->error = HPI_ERROR_MEMORY_ALLOC;
468
return;
469
}
470
471
ao.pci = *phm->u.s.resource.r.pci;
472
err = create_adapter_obj(&ao, &os_error_code);
473
if (err) {
474
delete_adapter_obj(&ao);
475
if (err >= HPI_ERROR_BACKEND_BASE) {
476
phr->error = HPI_ERROR_DSP_BOOTLOAD;
477
phr->specific_error = err;
478
} else {
479
phr->error = err;
480
}
481
phr->u.s.data = os_error_code;
482
return;
483
}
484
485
phr->u.s.adapter_type = ao.type;
486
phr->u.s.adapter_index = ao.index;
487
phr->error = 0;
488
}
489
490
/** delete an adapter - required by WDM driver */
491
static void adapter_delete(struct hpi_adapter_obj *pao,
492
struct hpi_message *phm, struct hpi_response *phr)
493
{
494
struct hpi_hw_obj *phw;
495
496
if (!pao) {
497
phr->error = HPI_ERROR_INVALID_OBJ_INDEX;
498
return;
499
}
500
phw = pao->priv;
501
/* reset adapter h/w */
502
/* Reset C6713 #1 */
503
boot_loader_write_mem32(pao, 0, C6205_BAR0_TIMER1_CTL, 0);
504
/* reset C6205 */
505
iowrite32(C6205_HDCR_WARMRESET, phw->prHDCR);
506
507
delete_adapter_obj(pao);
508
hpi_delete_adapter(pao);
509
phr->error = 0;
510
}
511
512
/** Create adapter object
513
allocate buffers, bootload DSPs, initialise control cache
514
*/
515
static u16 create_adapter_obj(struct hpi_adapter_obj *pao,
516
u32 *pos_error_code)
517
{
518
struct hpi_hw_obj *phw = pao->priv;
519
struct bus_master_interface *interface;
520
u32 phys_addr;
521
int i;
522
u16 err;
523
524
/* init error reporting */
525
pao->dsp_crashed = 0;
526
527
for (i = 0; i < HPI_MAX_STREAMS; i++)
528
phw->flag_outstream_just_reset[i] = 1;
529
530
/* The C6205 memory area 1 is 8Mbyte window into DSP registers */
531
phw->prHSR =
532
pao->pci.ap_mem_base[1] +
533
C6205_BAR1_HSR / sizeof(*pao->pci.ap_mem_base[1]);
534
phw->prHDCR =
535
pao->pci.ap_mem_base[1] +
536
C6205_BAR1_HDCR / sizeof(*pao->pci.ap_mem_base[1]);
537
phw->prDSPP =
538
pao->pci.ap_mem_base[1] +
539
C6205_BAR1_DSPP / sizeof(*pao->pci.ap_mem_base[1]);
540
541
pao->has_control_cache = 0;
542
543
if (hpios_locked_mem_alloc(&phw->h_locked_mem,
544
sizeof(struct bus_master_interface),
545
pao->pci.pci_dev))
546
phw->p_interface_buffer = NULL;
547
else if (hpios_locked_mem_get_virt_addr(&phw->h_locked_mem,
548
(void *)&phw->p_interface_buffer))
549
phw->p_interface_buffer = NULL;
550
551
HPI_DEBUG_LOG(DEBUG, "interface buffer address %p\n",
552
phw->p_interface_buffer);
553
554
if (phw->p_interface_buffer) {
555
memset((void *)phw->p_interface_buffer, 0,
556
sizeof(struct bus_master_interface));
557
phw->p_interface_buffer->dsp_ack = H620_HIF_UNKNOWN;
558
}
559
560
err = adapter_boot_load_dsp(pao, pos_error_code);
561
if (err) {
562
HPI_DEBUG_LOG(ERROR, "DSP code load failed\n");
563
/* no need to clean up as SubSysCreateAdapter */
564
/* calls DeleteAdapter on error. */
565
return err;
566
}
567
HPI_DEBUG_LOG(INFO, "load DSP code OK\n");
568
569
/* allow boot load even if mem alloc wont work */
570
if (!phw->p_interface_buffer)
571
return HPI_ERROR_MEMORY_ALLOC;
572
573
interface = phw->p_interface_buffer;
574
575
/* make sure the DSP has started ok */
576
if (!wait_dsp_ack(phw, H620_HIF_RESET, HPI6205_TIMEOUT * 10)) {
577
HPI_DEBUG_LOG(ERROR, "timed out waiting reset state \n");
578
return HPI6205_ERROR_6205_INIT_FAILED;
579
}
580
/* Note that *pao, *phw are zeroed after allocation,
581
* so pointers and flags are NULL by default.
582
* Allocate bus mastering control cache buffer and tell the DSP about it
583
*/
584
if (interface->control_cache.number_of_controls) {
585
u8 *p_control_cache_virtual;
586
587
err = hpios_locked_mem_alloc(&phw->h_control_cache,
588
interface->control_cache.size_in_bytes,
589
pao->pci.pci_dev);
590
if (!err)
591
err = hpios_locked_mem_get_virt_addr(&phw->
592
h_control_cache,
593
(void *)&p_control_cache_virtual);
594
if (!err) {
595
memset(p_control_cache_virtual, 0,
596
interface->control_cache.size_in_bytes);
597
598
phw->p_cache =
599
hpi_alloc_control_cache(interface->
600
control_cache.number_of_controls,
601
interface->control_cache.size_in_bytes,
602
p_control_cache_virtual);
603
604
if (!phw->p_cache)
605
err = HPI_ERROR_MEMORY_ALLOC;
606
}
607
if (!err) {
608
err = hpios_locked_mem_get_phys_addr(&phw->
609
h_control_cache, &phys_addr);
610
interface->control_cache.physical_address32 =
611
phys_addr;
612
}
613
614
if (!err)
615
pao->has_control_cache = 1;
616
else {
617
if (hpios_locked_mem_valid(&phw->h_control_cache))
618
hpios_locked_mem_free(&phw->h_control_cache);
619
pao->has_control_cache = 0;
620
}
621
}
622
send_dsp_command(phw, H620_HIF_IDLE);
623
624
{
625
struct hpi_message hm;
626
struct hpi_response hr;
627
628
HPI_DEBUG_LOG(VERBOSE, "init ADAPTER_GET_INFO\n");
629
memset(&hm, 0, sizeof(hm));
630
/* wAdapterIndex == version == 0 */
631
hm.type = HPI_TYPE_REQUEST;
632
hm.size = sizeof(hm);
633
hm.object = HPI_OBJ_ADAPTER;
634
hm.function = HPI_ADAPTER_GET_INFO;
635
636
memset(&hr, 0, sizeof(hr));
637
hr.size = sizeof(hr);
638
639
err = message_response_sequence(pao, &hm, &hr);
640
if (err) {
641
HPI_DEBUG_LOG(ERROR, "message transport error %d\n",
642
err);
643
return err;
644
}
645
if (hr.error)
646
return hr.error;
647
648
pao->type = hr.u.ax.info.adapter_type;
649
pao->index = hr.u.ax.info.adapter_index;
650
651
HPI_DEBUG_LOG(VERBOSE,
652
"got adapter info type %x index %d serial %d\n",
653
hr.u.ax.info.adapter_type, hr.u.ax.info.adapter_index,
654
hr.u.ax.info.serial_number);
655
}
656
657
if (phw->p_cache)
658
phw->p_cache->adap_idx = pao->index;
659
660
HPI_DEBUG_LOG(INFO, "bootload DSP OK\n");
661
662
pao->irq_query_and_clear = adapter_irq_query_and_clear;
663
pao->instream_host_buffer_status =
664
phw->p_interface_buffer->instream_host_buffer_status;
665
pao->outstream_host_buffer_status =
666
phw->p_interface_buffer->outstream_host_buffer_status;
667
668
return hpi_add_adapter(pao);
669
}
670
671
/** Free memory areas allocated by adapter
672
* this routine is called from AdapterDelete,
673
* and SubSysCreateAdapter if duplicate index
674
*/
675
static void delete_adapter_obj(struct hpi_adapter_obj *pao)
676
{
677
struct hpi_hw_obj *phw = pao->priv;
678
int i;
679
680
if (hpios_locked_mem_valid(&phw->h_control_cache)) {
681
hpios_locked_mem_free(&phw->h_control_cache);
682
hpi_free_control_cache(phw->p_cache);
683
}
684
685
if (hpios_locked_mem_valid(&phw->h_locked_mem)) {
686
hpios_locked_mem_free(&phw->h_locked_mem);
687
phw->p_interface_buffer = NULL;
688
}
689
690
for (i = 0; i < HPI_MAX_STREAMS; i++)
691
if (hpios_locked_mem_valid(&phw->instream_host_buffers[i])) {
692
hpios_locked_mem_free(&phw->instream_host_buffers[i]);
693
/*?phw->InStreamHostBuffers[i] = NULL; */
694
phw->instream_host_buffer_size[i] = 0;
695
}
696
697
for (i = 0; i < HPI_MAX_STREAMS; i++)
698
if (hpios_locked_mem_valid(&phw->outstream_host_buffers[i])) {
699
hpios_locked_mem_free(&phw->outstream_host_buffers
700
[i]);
701
phw->outstream_host_buffer_size[i] = 0;
702
}
703
kfree(phw);
704
}
705
706
/*****************************************************************************/
707
/* Adapter functions */
708
static int adapter_irq_query_and_clear(struct hpi_adapter_obj *pao,
709
u32 message)
710
{
711
struct hpi_hw_obj *phw = pao->priv;
712
u32 hsr = 0;
713
714
hsr = ioread32(phw->prHSR);
715
if (hsr & C6205_HSR_INTSRC) {
716
/* reset the interrupt from the DSP */
717
iowrite32(C6205_HSR_INTSRC, phw->prHSR);
718
return HPI_IRQ_MIXER;
719
}
720
721
return HPI_IRQ_NONE;
722
}
723
724
/*****************************************************************************/
725
/* OutStream Host buffer functions */
726
727
/** Allocate or attach buffer for busmastering
728
*/
729
static void outstream_host_buffer_allocate(struct hpi_adapter_obj *pao,
730
struct hpi_message *phm, struct hpi_response *phr)
731
{
732
u16 err = 0;
733
u32 command = phm->u.d.u.buffer.command;
734
struct hpi_hw_obj *phw = pao->priv;
735
struct bus_master_interface *interface = phw->p_interface_buffer;
736
737
hpi_init_response(phr, phm->object, phm->function, 0);
738
739
if (command == HPI_BUFFER_CMD_EXTERNAL
740
|| command == HPI_BUFFER_CMD_INTERNAL_ALLOC) {
741
/* ALLOC phase, allocate a buffer with power of 2 size,
742
get its bus address for PCI bus mastering
743
*/
744
phm->u.d.u.buffer.buffer_size =
745
roundup_pow_of_two(phm->u.d.u.buffer.buffer_size);
746
/* return old size and allocated size,
747
so caller can detect change */
748
phr->u.d.u.stream_info.data_available =
749
phw->outstream_host_buffer_size[phm->obj_index];
750
phr->u.d.u.stream_info.buffer_size =
751
phm->u.d.u.buffer.buffer_size;
752
753
if (phw->outstream_host_buffer_size[phm->obj_index] ==
754
phm->u.d.u.buffer.buffer_size) {
755
/* Same size, no action required */
756
return;
757
}
758
759
if (hpios_locked_mem_valid(&phw->outstream_host_buffers[phm->
760
obj_index]))
761
hpios_locked_mem_free(&phw->outstream_host_buffers
762
[phm->obj_index]);
763
764
err = hpios_locked_mem_alloc(&phw->outstream_host_buffers
765
[phm->obj_index], phm->u.d.u.buffer.buffer_size,
766
pao->pci.pci_dev);
767
768
if (err) {
769
phr->error = HPI_ERROR_INVALID_DATASIZE;
770
phw->outstream_host_buffer_size[phm->obj_index] = 0;
771
return;
772
}
773
774
err = hpios_locked_mem_get_phys_addr
775
(&phw->outstream_host_buffers[phm->obj_index],
776
&phm->u.d.u.buffer.pci_address);
777
/* get the phys addr into msg for single call alloc caller
778
* needs to do this for split alloc (or use the same message)
779
* return the phy address for split alloc in the respose too
780
*/
781
phr->u.d.u.stream_info.auxiliary_data_available =
782
phm->u.d.u.buffer.pci_address;
783
784
if (err) {
785
hpios_locked_mem_free(&phw->outstream_host_buffers
786
[phm->obj_index]);
787
phw->outstream_host_buffer_size[phm->obj_index] = 0;
788
phr->error = HPI_ERROR_MEMORY_ALLOC;
789
return;
790
}
791
}
792
793
if (command == HPI_BUFFER_CMD_EXTERNAL
794
|| command == HPI_BUFFER_CMD_INTERNAL_GRANTADAPTER) {
795
/* GRANT phase. Set up the BBM status, tell the DSP about
796
the buffer so it can start using BBM.
797
*/
798
struct hpi_hostbuffer_status *status;
799
800
if (phm->u.d.u.buffer.buffer_size & (phm->u.d.u.buffer.
801
buffer_size - 1)) {
802
HPI_DEBUG_LOG(ERROR,
803
"Buffer size must be 2^N not %d\n",
804
phm->u.d.u.buffer.buffer_size);
805
phr->error = HPI_ERROR_INVALID_DATASIZE;
806
return;
807
}
808
phw->outstream_host_buffer_size[phm->obj_index] =
809
phm->u.d.u.buffer.buffer_size;
810
status = &interface->outstream_host_buffer_status[phm->
811
obj_index];
812
status->samples_processed = 0;
813
status->stream_state = HPI_STATE_STOPPED;
814
status->dsp_index = 0;
815
status->host_index = status->dsp_index;
816
status->size_in_bytes = phm->u.d.u.buffer.buffer_size;
817
status->auxiliary_data_available = 0;
818
819
hw_message(pao, phm, phr);
820
821
if (phr->error
822
&& hpios_locked_mem_valid(&phw->
823
outstream_host_buffers[phm->obj_index])) {
824
hpios_locked_mem_free(&phw->outstream_host_buffers
825
[phm->obj_index]);
826
phw->outstream_host_buffer_size[phm->obj_index] = 0;
827
}
828
}
829
}
830
831
static void outstream_host_buffer_get_info(struct hpi_adapter_obj *pao,
832
struct hpi_message *phm, struct hpi_response *phr)
833
{
834
struct hpi_hw_obj *phw = pao->priv;
835
struct bus_master_interface *interface = phw->p_interface_buffer;
836
struct hpi_hostbuffer_status *status;
837
u8 *p_bbm_data;
838
839
if (hpios_locked_mem_valid(&phw->outstream_host_buffers[phm->
840
obj_index])) {
841
if (hpios_locked_mem_get_virt_addr(&phw->
842
outstream_host_buffers[phm->obj_index],
843
(void *)&p_bbm_data)) {
844
phr->error = HPI_ERROR_INVALID_OPERATION;
845
return;
846
}
847
status = &interface->outstream_host_buffer_status[phm->
848
obj_index];
849
hpi_init_response(phr, HPI_OBJ_OSTREAM,
850
HPI_OSTREAM_HOSTBUFFER_GET_INFO, 0);
851
phr->u.d.u.hostbuffer_info.p_buffer = p_bbm_data;
852
phr->u.d.u.hostbuffer_info.p_status = status;
853
} else {
854
hpi_init_response(phr, HPI_OBJ_OSTREAM,
855
HPI_OSTREAM_HOSTBUFFER_GET_INFO,
856
HPI_ERROR_INVALID_OPERATION);
857
}
858
}
859
860
static void outstream_host_buffer_free(struct hpi_adapter_obj *pao,
861
struct hpi_message *phm, struct hpi_response *phr)
862
{
863
struct hpi_hw_obj *phw = pao->priv;
864
u32 command = phm->u.d.u.buffer.command;
865
866
if (phw->outstream_host_buffer_size[phm->obj_index]) {
867
if (command == HPI_BUFFER_CMD_EXTERNAL
868
|| command == HPI_BUFFER_CMD_INTERNAL_REVOKEADAPTER) {
869
phw->outstream_host_buffer_size[phm->obj_index] = 0;
870
hw_message(pao, phm, phr);
871
/* Tell adapter to stop using the host buffer. */
872
}
873
if (command == HPI_BUFFER_CMD_EXTERNAL
874
|| command == HPI_BUFFER_CMD_INTERNAL_FREE)
875
hpios_locked_mem_free(&phw->outstream_host_buffers
876
[phm->obj_index]);
877
}
878
/* Should HPI_ERROR_INVALID_OPERATION be returned
879
if no host buffer is allocated? */
880
else
881
hpi_init_response(phr, HPI_OBJ_OSTREAM,
882
HPI_OSTREAM_HOSTBUFFER_FREE, 0);
883
884
}
885
886
static u32 outstream_get_space_available(struct hpi_hostbuffer_status *status)
887
{
888
return status->size_in_bytes - (status->host_index -
889
status->dsp_index);
890
}
891
892
static void outstream_write(struct hpi_adapter_obj *pao,
893
struct hpi_message *phm, struct hpi_response *phr)
894
{
895
struct hpi_hw_obj *phw = pao->priv;
896
struct bus_master_interface *interface = phw->p_interface_buffer;
897
struct hpi_hostbuffer_status *status;
898
u32 space_available;
899
900
if (!phw->outstream_host_buffer_size[phm->obj_index]) {
901
/* there is no BBM buffer, write via message */
902
hw_message(pao, phm, phr);
903
return;
904
}
905
906
hpi_init_response(phr, phm->object, phm->function, 0);
907
status = &interface->outstream_host_buffer_status[phm->obj_index];
908
909
space_available = outstream_get_space_available(status);
910
if (space_available < phm->u.d.u.data.data_size) {
911
phr->error = HPI_ERROR_INVALID_DATASIZE;
912
return;
913
}
914
915
/* HostBuffers is used to indicate host buffer is internally allocated.
916
otherwise, assumed external, data written externally */
917
if (phm->u.d.u.data.pb_data
918
&& hpios_locked_mem_valid(&phw->outstream_host_buffers[phm->
919
obj_index])) {
920
u8 *p_bbm_data;
921
u32 l_first_write;
922
u8 *p_app_data = (u8 *)phm->u.d.u.data.pb_data;
923
924
if (hpios_locked_mem_get_virt_addr(&phw->
925
outstream_host_buffers[phm->obj_index],
926
(void *)&p_bbm_data)) {
927
phr->error = HPI_ERROR_INVALID_OPERATION;
928
return;
929
}
930
931
/* either all data,
932
or enough to fit from current to end of BBM buffer */
933
l_first_write =
934
min(phm->u.d.u.data.data_size,
935
status->size_in_bytes -
936
(status->host_index & (status->size_in_bytes - 1)));
937
938
memcpy(p_bbm_data +
939
(status->host_index & (status->size_in_bytes - 1)),
940
p_app_data, l_first_write);
941
/* remaining data if any */
942
memcpy(p_bbm_data, p_app_data + l_first_write,
943
phm->u.d.u.data.data_size - l_first_write);
944
}
945
946
/*
947
* This version relies on the DSP code triggering an OStream buffer
948
* update immediately following a SET_FORMAT call. The host has
949
* already written data into the BBM buffer, but the DSP won't know
950
* about it until dwHostIndex is adjusted.
951
*/
952
if (phw->flag_outstream_just_reset[phm->obj_index]) {
953
/* Format can only change after reset. Must tell DSP. */
954
u16 function = phm->function;
955
phw->flag_outstream_just_reset[phm->obj_index] = 0;
956
phm->function = HPI_OSTREAM_SET_FORMAT;
957
hw_message(pao, phm, phr); /* send the format to the DSP */
958
phm->function = function;
959
if (phr->error)
960
return;
961
}
962
963
status->host_index += phm->u.d.u.data.data_size;
964
}
965
966
static void outstream_get_info(struct hpi_adapter_obj *pao,
967
struct hpi_message *phm, struct hpi_response *phr)
968
{
969
struct hpi_hw_obj *phw = pao->priv;
970
struct bus_master_interface *interface = phw->p_interface_buffer;
971
struct hpi_hostbuffer_status *status;
972
973
if (!phw->outstream_host_buffer_size[phm->obj_index]) {
974
hw_message(pao, phm, phr);
975
return;
976
}
977
978
hpi_init_response(phr, phm->object, phm->function, 0);
979
980
status = &interface->outstream_host_buffer_status[phm->obj_index];
981
982
phr->u.d.u.stream_info.state = (u16)status->stream_state;
983
phr->u.d.u.stream_info.samples_transferred =
984
status->samples_processed;
985
phr->u.d.u.stream_info.buffer_size = status->size_in_bytes;
986
phr->u.d.u.stream_info.data_available =
987
status->size_in_bytes - outstream_get_space_available(status);
988
phr->u.d.u.stream_info.auxiliary_data_available =
989
status->auxiliary_data_available;
990
}
991
992
static void outstream_start(struct hpi_adapter_obj *pao,
993
struct hpi_message *phm, struct hpi_response *phr)
994
{
995
hw_message(pao, phm, phr);
996
}
997
998
static void outstream_reset(struct hpi_adapter_obj *pao,
999
struct hpi_message *phm, struct hpi_response *phr)
1000
{
1001
struct hpi_hw_obj *phw = pao->priv;
1002
phw->flag_outstream_just_reset[phm->obj_index] = 1;
1003
hw_message(pao, phm, phr);
1004
}
1005
1006
static void outstream_open(struct hpi_adapter_obj *pao,
1007
struct hpi_message *phm, struct hpi_response *phr)
1008
{
1009
outstream_reset(pao, phm, phr);
1010
}
1011
1012
/*****************************************************************************/
1013
/* InStream Host buffer functions */
1014
1015
static void instream_host_buffer_allocate(struct hpi_adapter_obj *pao,
1016
struct hpi_message *phm, struct hpi_response *phr)
1017
{
1018
u16 err = 0;
1019
u32 command = phm->u.d.u.buffer.command;
1020
struct hpi_hw_obj *phw = pao->priv;
1021
struct bus_master_interface *interface = phw->p_interface_buffer;
1022
1023
hpi_init_response(phr, phm->object, phm->function, 0);
1024
1025
if (command == HPI_BUFFER_CMD_EXTERNAL
1026
|| command == HPI_BUFFER_CMD_INTERNAL_ALLOC) {
1027
1028
phm->u.d.u.buffer.buffer_size =
1029
roundup_pow_of_two(phm->u.d.u.buffer.buffer_size);
1030
phr->u.d.u.stream_info.data_available =
1031
phw->instream_host_buffer_size[phm->obj_index];
1032
phr->u.d.u.stream_info.buffer_size =
1033
phm->u.d.u.buffer.buffer_size;
1034
1035
if (phw->instream_host_buffer_size[phm->obj_index] ==
1036
phm->u.d.u.buffer.buffer_size) {
1037
/* Same size, no action required */
1038
return;
1039
}
1040
1041
if (hpios_locked_mem_valid(&phw->instream_host_buffers[phm->
1042
obj_index]))
1043
hpios_locked_mem_free(&phw->instream_host_buffers
1044
[phm->obj_index]);
1045
1046
err = hpios_locked_mem_alloc(&phw->instream_host_buffers[phm->
1047
obj_index], phm->u.d.u.buffer.buffer_size,
1048
pao->pci.pci_dev);
1049
1050
if (err) {
1051
phr->error = HPI_ERROR_INVALID_DATASIZE;
1052
phw->instream_host_buffer_size[phm->obj_index] = 0;
1053
return;
1054
}
1055
1056
err = hpios_locked_mem_get_phys_addr
1057
(&phw->instream_host_buffers[phm->obj_index],
1058
&phm->u.d.u.buffer.pci_address);
1059
/* get the phys addr into msg for single call alloc. Caller
1060
needs to do this for split alloc so return the phy address */
1061
phr->u.d.u.stream_info.auxiliary_data_available =
1062
phm->u.d.u.buffer.pci_address;
1063
if (err) {
1064
hpios_locked_mem_free(&phw->instream_host_buffers
1065
[phm->obj_index]);
1066
phw->instream_host_buffer_size[phm->obj_index] = 0;
1067
phr->error = HPI_ERROR_MEMORY_ALLOC;
1068
return;
1069
}
1070
}
1071
1072
if (command == HPI_BUFFER_CMD_EXTERNAL
1073
|| command == HPI_BUFFER_CMD_INTERNAL_GRANTADAPTER) {
1074
struct hpi_hostbuffer_status *status;
1075
1076
if (phm->u.d.u.buffer.buffer_size & (phm->u.d.u.buffer.
1077
buffer_size - 1)) {
1078
HPI_DEBUG_LOG(ERROR,
1079
"Buffer size must be 2^N not %d\n",
1080
phm->u.d.u.buffer.buffer_size);
1081
phr->error = HPI_ERROR_INVALID_DATASIZE;
1082
return;
1083
}
1084
1085
phw->instream_host_buffer_size[phm->obj_index] =
1086
phm->u.d.u.buffer.buffer_size;
1087
status = &interface->instream_host_buffer_status[phm->
1088
obj_index];
1089
status->samples_processed = 0;
1090
status->stream_state = HPI_STATE_STOPPED;
1091
status->dsp_index = 0;
1092
status->host_index = status->dsp_index;
1093
status->size_in_bytes = phm->u.d.u.buffer.buffer_size;
1094
status->auxiliary_data_available = 0;
1095
1096
hw_message(pao, phm, phr);
1097
1098
if (phr->error
1099
&& hpios_locked_mem_valid(&phw->
1100
instream_host_buffers[phm->obj_index])) {
1101
hpios_locked_mem_free(&phw->instream_host_buffers
1102
[phm->obj_index]);
1103
phw->instream_host_buffer_size[phm->obj_index] = 0;
1104
}
1105
}
1106
}
1107
1108
static void instream_host_buffer_get_info(struct hpi_adapter_obj *pao,
1109
struct hpi_message *phm, struct hpi_response *phr)
1110
{
1111
struct hpi_hw_obj *phw = pao->priv;
1112
struct bus_master_interface *interface = phw->p_interface_buffer;
1113
struct hpi_hostbuffer_status *status;
1114
u8 *p_bbm_data;
1115
1116
if (hpios_locked_mem_valid(&phw->instream_host_buffers[phm->
1117
obj_index])) {
1118
if (hpios_locked_mem_get_virt_addr(&phw->
1119
instream_host_buffers[phm->obj_index],
1120
(void *)&p_bbm_data)) {
1121
phr->error = HPI_ERROR_INVALID_OPERATION;
1122
return;
1123
}
1124
status = &interface->instream_host_buffer_status[phm->
1125
obj_index];
1126
hpi_init_response(phr, HPI_OBJ_ISTREAM,
1127
HPI_ISTREAM_HOSTBUFFER_GET_INFO, 0);
1128
phr->u.d.u.hostbuffer_info.p_buffer = p_bbm_data;
1129
phr->u.d.u.hostbuffer_info.p_status = status;
1130
} else {
1131
hpi_init_response(phr, HPI_OBJ_ISTREAM,
1132
HPI_ISTREAM_HOSTBUFFER_GET_INFO,
1133
HPI_ERROR_INVALID_OPERATION);
1134
}
1135
}
1136
1137
static void instream_host_buffer_free(struct hpi_adapter_obj *pao,
1138
struct hpi_message *phm, struct hpi_response *phr)
1139
{
1140
struct hpi_hw_obj *phw = pao->priv;
1141
u32 command = phm->u.d.u.buffer.command;
1142
1143
if (phw->instream_host_buffer_size[phm->obj_index]) {
1144
if (command == HPI_BUFFER_CMD_EXTERNAL
1145
|| command == HPI_BUFFER_CMD_INTERNAL_REVOKEADAPTER) {
1146
phw->instream_host_buffer_size[phm->obj_index] = 0;
1147
hw_message(pao, phm, phr);
1148
}
1149
1150
if (command == HPI_BUFFER_CMD_EXTERNAL
1151
|| command == HPI_BUFFER_CMD_INTERNAL_FREE)
1152
hpios_locked_mem_free(&phw->instream_host_buffers
1153
[phm->obj_index]);
1154
1155
} else {
1156
/* Should HPI_ERROR_INVALID_OPERATION be returned
1157
if no host buffer is allocated? */
1158
hpi_init_response(phr, HPI_OBJ_ISTREAM,
1159
HPI_ISTREAM_HOSTBUFFER_FREE, 0);
1160
1161
}
1162
1163
}
1164
1165
static void instream_start(struct hpi_adapter_obj *pao,
1166
struct hpi_message *phm, struct hpi_response *phr)
1167
{
1168
hw_message(pao, phm, phr);
1169
}
1170
1171
static u32 instream_get_bytes_available(struct hpi_hostbuffer_status *status)
1172
{
1173
return status->dsp_index - status->host_index;
1174
}
1175
1176
static void instream_read(struct hpi_adapter_obj *pao,
1177
struct hpi_message *phm, struct hpi_response *phr)
1178
{
1179
struct hpi_hw_obj *phw = pao->priv;
1180
struct bus_master_interface *interface = phw->p_interface_buffer;
1181
struct hpi_hostbuffer_status *status;
1182
u32 data_available;
1183
u8 *p_bbm_data;
1184
u32 l_first_read;
1185
u8 *p_app_data = (u8 *)phm->u.d.u.data.pb_data;
1186
1187
if (!phw->instream_host_buffer_size[phm->obj_index]) {
1188
hw_message(pao, phm, phr);
1189
return;
1190
}
1191
hpi_init_response(phr, phm->object, phm->function, 0);
1192
1193
status = &interface->instream_host_buffer_status[phm->obj_index];
1194
data_available = instream_get_bytes_available(status);
1195
if (data_available < phm->u.d.u.data.data_size) {
1196
phr->error = HPI_ERROR_INVALID_DATASIZE;
1197
return;
1198
}
1199
1200
if (hpios_locked_mem_valid(&phw->instream_host_buffers[phm->
1201
obj_index])) {
1202
if (hpios_locked_mem_get_virt_addr(&phw->
1203
instream_host_buffers[phm->obj_index],
1204
(void *)&p_bbm_data)) {
1205
phr->error = HPI_ERROR_INVALID_OPERATION;
1206
return;
1207
}
1208
1209
/* either all data,
1210
or enough to fit from current to end of BBM buffer */
1211
l_first_read =
1212
min(phm->u.d.u.data.data_size,
1213
status->size_in_bytes -
1214
(status->host_index & (status->size_in_bytes - 1)));
1215
1216
memcpy(p_app_data,
1217
p_bbm_data +
1218
(status->host_index & (status->size_in_bytes - 1)),
1219
l_first_read);
1220
/* remaining data if any */
1221
memcpy(p_app_data + l_first_read, p_bbm_data,
1222
phm->u.d.u.data.data_size - l_first_read);
1223
}
1224
status->host_index += phm->u.d.u.data.data_size;
1225
}
1226
1227
static void instream_get_info(struct hpi_adapter_obj *pao,
1228
struct hpi_message *phm, struct hpi_response *phr)
1229
{
1230
struct hpi_hw_obj *phw = pao->priv;
1231
struct bus_master_interface *interface = phw->p_interface_buffer;
1232
struct hpi_hostbuffer_status *status;
1233
if (!phw->instream_host_buffer_size[phm->obj_index]) {
1234
hw_message(pao, phm, phr);
1235
return;
1236
}
1237
1238
status = &interface->instream_host_buffer_status[phm->obj_index];
1239
1240
hpi_init_response(phr, phm->object, phm->function, 0);
1241
1242
phr->u.d.u.stream_info.state = (u16)status->stream_state;
1243
phr->u.d.u.stream_info.samples_transferred =
1244
status->samples_processed;
1245
phr->u.d.u.stream_info.buffer_size = status->size_in_bytes;
1246
phr->u.d.u.stream_info.data_available =
1247
instream_get_bytes_available(status);
1248
phr->u.d.u.stream_info.auxiliary_data_available =
1249
status->auxiliary_data_available;
1250
}
1251
1252
/*****************************************************************************/
1253
/* LOW-LEVEL */
1254
#define HPI6205_MAX_FILES_TO_LOAD 2
1255
1256
static u16 adapter_boot_load_dsp(struct hpi_adapter_obj *pao,
1257
u32 *pos_error_code)
1258
{
1259
struct hpi_hw_obj *phw = pao->priv;
1260
struct dsp_code dsp_code;
1261
u16 boot_code_id[HPI6205_MAX_FILES_TO_LOAD];
1262
u32 temp;
1263
int dsp = 0, i = 0;
1264
u16 err = 0;
1265
1266
boot_code_id[0] = HPI_ADAPTER_ASI(0x6205);
1267
1268
boot_code_id[1] = pao->pci.pci_dev->subsystem_device;
1269
boot_code_id[1] = HPI_ADAPTER_FAMILY_ASI(boot_code_id[1]);
1270
1271
/* fix up cases where bootcode id[1] != subsys id */
1272
switch (boot_code_id[1]) {
1273
case HPI_ADAPTER_FAMILY_ASI(0x5000):
1274
boot_code_id[0] = boot_code_id[1];
1275
boot_code_id[1] = 0;
1276
break;
1277
case HPI_ADAPTER_FAMILY_ASI(0x5300):
1278
case HPI_ADAPTER_FAMILY_ASI(0x5400):
1279
case HPI_ADAPTER_FAMILY_ASI(0x6300):
1280
boot_code_id[1] = HPI_ADAPTER_FAMILY_ASI(0x6400);
1281
break;
1282
case HPI_ADAPTER_FAMILY_ASI(0x5500):
1283
case HPI_ADAPTER_FAMILY_ASI(0x5600):
1284
case HPI_ADAPTER_FAMILY_ASI(0x6500):
1285
boot_code_id[1] = HPI_ADAPTER_FAMILY_ASI(0x6600);
1286
break;
1287
case HPI_ADAPTER_FAMILY_ASI(0x8800):
1288
boot_code_id[1] = HPI_ADAPTER_FAMILY_ASI(0x8900);
1289
break;
1290
default:
1291
break;
1292
}
1293
1294
/* reset DSP by writing a 1 to the WARMRESET bit */
1295
temp = C6205_HDCR_WARMRESET;
1296
iowrite32(temp, phw->prHDCR);
1297
hpios_delay_micro_seconds(1000);
1298
1299
/* check that PCI i/f was configured by EEPROM */
1300
temp = ioread32(phw->prHSR);
1301
if ((temp & (C6205_HSR_CFGERR | C6205_HSR_EEREAD)) !=
1302
C6205_HSR_EEREAD)
1303
return HPI6205_ERROR_6205_EEPROM;
1304
temp |= 0x04;
1305
/* disable PINTA interrupt */
1306
iowrite32(temp, phw->prHSR);
1307
1308
/* check control register reports PCI boot mode */
1309
temp = ioread32(phw->prHDCR);
1310
if (!(temp & C6205_HDCR_PCIBOOT))
1311
return HPI6205_ERROR_6205_REG;
1312
1313
/* try writing a few numbers to the DSP page register */
1314
/* and reading them back. */
1315
temp = 3;
1316
iowrite32(temp, phw->prDSPP);
1317
if ((temp | C6205_DSPP_MAP1) != ioread32(phw->prDSPP))
1318
return HPI6205_ERROR_6205_DSPPAGE;
1319
temp = 2;
1320
iowrite32(temp, phw->prDSPP);
1321
if ((temp | C6205_DSPP_MAP1) != ioread32(phw->prDSPP))
1322
return HPI6205_ERROR_6205_DSPPAGE;
1323
temp = 1;
1324
iowrite32(temp, phw->prDSPP);
1325
if ((temp | C6205_DSPP_MAP1) != ioread32(phw->prDSPP))
1326
return HPI6205_ERROR_6205_DSPPAGE;
1327
/* reset DSP page to the correct number */
1328
temp = 0;
1329
iowrite32(temp, phw->prDSPP);
1330
if ((temp | C6205_DSPP_MAP1) != ioread32(phw->prDSPP))
1331
return HPI6205_ERROR_6205_DSPPAGE;
1332
phw->dsp_page = 0;
1333
1334
/* release 6713 from reset before 6205 is bootloaded.
1335
This ensures that the EMIF is inactive,
1336
and the 6713 HPI gets the correct bootmode etc
1337
*/
1338
if (boot_code_id[1] != 0) {
1339
/* DSP 1 is a C6713 */
1340
/* CLKX0 <- '1' release the C6205 bootmode pulldowns */
1341
boot_loader_write_mem32(pao, 0, 0x018C0024, 0x00002202);
1342
hpios_delay_micro_seconds(100);
1343
/* Reset the 6713 #1 - revB */
1344
boot_loader_write_mem32(pao, 0, C6205_BAR0_TIMER1_CTL, 0);
1345
/* value of bit 3 is unknown after DSP reset, other bits shoudl be 0 */
1346
if (0 != (boot_loader_read_mem32(pao, 0,
1347
(C6205_BAR0_TIMER1_CTL)) & ~8))
1348
return HPI6205_ERROR_6205_REG;
1349
hpios_delay_micro_seconds(100);
1350
1351
/* Release C6713 from reset - revB */
1352
boot_loader_write_mem32(pao, 0, C6205_BAR0_TIMER1_CTL, 4);
1353
if (4 != (boot_loader_read_mem32(pao, 0,
1354
(C6205_BAR0_TIMER1_CTL)) & ~8))
1355
return HPI6205_ERROR_6205_REG;
1356
hpios_delay_micro_seconds(100);
1357
}
1358
1359
for (dsp = 0; dsp < HPI6205_MAX_FILES_TO_LOAD; dsp++) {
1360
/* is there a DSP to load? */
1361
if (boot_code_id[dsp] == 0)
1362
continue;
1363
1364
err = boot_loader_config_emif(pao, dsp);
1365
if (err)
1366
return err;
1367
1368
err = boot_loader_test_internal_memory(pao, dsp);
1369
if (err)
1370
return err;
1371
1372
err = boot_loader_test_external_memory(pao, dsp);
1373
if (err)
1374
return err;
1375
1376
err = boot_loader_test_pld(pao, dsp);
1377
if (err)
1378
return err;
1379
1380
/* write the DSP code down into the DSPs memory */
1381
err = hpi_dsp_code_open(boot_code_id[dsp], pao->pci.pci_dev,
1382
&dsp_code, pos_error_code);
1383
if (err)
1384
return err;
1385
1386
while (1) {
1387
u32 length;
1388
u32 address;
1389
u32 type;
1390
u32 *pcode;
1391
1392
err = hpi_dsp_code_read_word(&dsp_code, &length);
1393
if (err)
1394
break;
1395
if (length == 0xFFFFFFFF)
1396
break; /* end of code */
1397
1398
err = hpi_dsp_code_read_word(&dsp_code, &address);
1399
if (err)
1400
break;
1401
err = hpi_dsp_code_read_word(&dsp_code, &type);
1402
if (err)
1403
break;
1404
err = hpi_dsp_code_read_block(length, &dsp_code,
1405
&pcode);
1406
if (err)
1407
break;
1408
for (i = 0; i < (int)length; i++) {
1409
boot_loader_write_mem32(pao, dsp, address,
1410
*pcode);
1411
/* dummy read every 4 words */
1412
/* for 6205 advisory 1.4.4 */
1413
if (i % 4 == 0)
1414
boot_loader_read_mem32(pao, dsp,
1415
address);
1416
pcode++;
1417
address += 4;
1418
}
1419
1420
}
1421
if (err) {
1422
hpi_dsp_code_close(&dsp_code);
1423
return err;
1424
}
1425
1426
/* verify code */
1427
hpi_dsp_code_rewind(&dsp_code);
1428
while (1) {
1429
u32 length = 0;
1430
u32 address = 0;
1431
u32 type = 0;
1432
u32 *pcode = NULL;
1433
u32 data = 0;
1434
1435
hpi_dsp_code_read_word(&dsp_code, &length);
1436
if (length == 0xFFFFFFFF)
1437
break; /* end of code */
1438
1439
hpi_dsp_code_read_word(&dsp_code, &address);
1440
hpi_dsp_code_read_word(&dsp_code, &type);
1441
hpi_dsp_code_read_block(length, &dsp_code, &pcode);
1442
1443
for (i = 0; i < (int)length; i++) {
1444
data = boot_loader_read_mem32(pao, dsp,
1445
address);
1446
if (data != *pcode) {
1447
err = 0;
1448
break;
1449
}
1450
pcode++;
1451
address += 4;
1452
}
1453
if (err)
1454
break;
1455
}
1456
hpi_dsp_code_close(&dsp_code);
1457
if (err)
1458
return err;
1459
}
1460
1461
/* After bootloading all DSPs, start DSP0 running
1462
* The DSP0 code will handle starting and synchronizing with its slaves
1463
*/
1464
if (phw->p_interface_buffer) {
1465
/* we need to tell the card the physical PCI address */
1466
u32 physicalPC_iaddress;
1467
struct bus_master_interface *interface =
1468
phw->p_interface_buffer;
1469
u32 host_mailbox_address_on_dsp;
1470
u32 physicalPC_iaddress_verify = 0;
1471
int time_out = 10;
1472
/* set ack so we know when DSP is ready to go */
1473
/* (dwDspAck will be changed to HIF_RESET) */
1474
interface->dsp_ack = H620_HIF_UNKNOWN;
1475
wmb(); /* ensure ack is written before dsp writes back */
1476
1477
err = hpios_locked_mem_get_phys_addr(&phw->h_locked_mem,
1478
&physicalPC_iaddress);
1479
1480
/* locate the host mailbox on the DSP. */
1481
host_mailbox_address_on_dsp = 0x80000000;
1482
while ((physicalPC_iaddress != physicalPC_iaddress_verify)
1483
&& time_out--) {
1484
boot_loader_write_mem32(pao, 0,
1485
host_mailbox_address_on_dsp,
1486
physicalPC_iaddress);
1487
physicalPC_iaddress_verify =
1488
boot_loader_read_mem32(pao, 0,
1489
host_mailbox_address_on_dsp);
1490
}
1491
}
1492
HPI_DEBUG_LOG(DEBUG, "starting DS_ps running\n");
1493
/* enable interrupts */
1494
temp = ioread32(phw->prHSR);
1495
temp &= ~(u32)C6205_HSR_INTAM;
1496
iowrite32(temp, phw->prHSR);
1497
1498
/* start code running... */
1499
temp = ioread32(phw->prHDCR);
1500
temp |= (u32)C6205_HDCR_DSPINT;
1501
iowrite32(temp, phw->prHDCR);
1502
1503
/* give the DSP 10ms to start up */
1504
hpios_delay_micro_seconds(10000);
1505
return err;
1506
1507
}
1508
1509
/*****************************************************************************/
1510
/* Bootloader utility functions */
1511
1512
static u32 boot_loader_read_mem32(struct hpi_adapter_obj *pao, int dsp_index,
1513
u32 address)
1514
{
1515
struct hpi_hw_obj *phw = pao->priv;
1516
u32 data = 0;
1517
__iomem u32 *p_data;
1518
1519
if (dsp_index == 0) {
1520
/* DSP 0 is always C6205 */
1521
if ((address >= 0x01800000) & (address < 0x02000000)) {
1522
/* BAR1 register access */
1523
p_data = pao->pci.ap_mem_base[1] +
1524
(address & 0x007fffff) /
1525
sizeof(*pao->pci.ap_mem_base[1]);
1526
/* HPI_DEBUG_LOG(WARNING,
1527
"BAR1 access %08x\n", dwAddress); */
1528
} else {
1529
u32 dw4M_page = address >> 22L;
1530
if (dw4M_page != phw->dsp_page) {
1531
phw->dsp_page = dw4M_page;
1532
/* *INDENT OFF* */
1533
iowrite32(phw->dsp_page, phw->prDSPP);
1534
/* *INDENT-ON* */
1535
}
1536
address &= 0x3fffff; /* address within 4M page */
1537
/* BAR0 memory access */
1538
p_data = pao->pci.ap_mem_base[0] +
1539
address / sizeof(u32);
1540
}
1541
data = ioread32(p_data);
1542
} else if (dsp_index == 1) {
1543
/* DSP 1 is a C6713 */
1544
u32 lsb;
1545
boot_loader_write_mem32(pao, 0, HPIAL_ADDR, address);
1546
boot_loader_write_mem32(pao, 0, HPIAH_ADDR, address >> 16);
1547
lsb = boot_loader_read_mem32(pao, 0, HPIDL_ADDR);
1548
data = boot_loader_read_mem32(pao, 0, HPIDH_ADDR);
1549
data = (data << 16) | (lsb & 0xFFFF);
1550
}
1551
return data;
1552
}
1553
1554
static void boot_loader_write_mem32(struct hpi_adapter_obj *pao,
1555
int dsp_index, u32 address, u32 data)
1556
{
1557
struct hpi_hw_obj *phw = pao->priv;
1558
__iomem u32 *p_data;
1559
/* u32 dwVerifyData=0; */
1560
1561
if (dsp_index == 0) {
1562
/* DSP 0 is always C6205 */
1563
if ((address >= 0x01800000) & (address < 0x02000000)) {
1564
/* BAR1 - DSP register access using */
1565
/* Non-prefetchable PCI access */
1566
p_data = pao->pci.ap_mem_base[1] +
1567
(address & 0x007fffff) /
1568
sizeof(*pao->pci.ap_mem_base[1]);
1569
} else {
1570
/* BAR0 access - all of DSP memory using */
1571
/* pre-fetchable PCI access */
1572
u32 dw4M_page = address >> 22L;
1573
if (dw4M_page != phw->dsp_page) {
1574
phw->dsp_page = dw4M_page;
1575
/* *INDENT-OFF* */
1576
iowrite32(phw->dsp_page, phw->prDSPP);
1577
/* *INDENT-ON* */
1578
}
1579
address &= 0x3fffff; /* address within 4M page */
1580
p_data = pao->pci.ap_mem_base[0] +
1581
address / sizeof(u32);
1582
}
1583
iowrite32(data, p_data);
1584
} else if (dsp_index == 1) {
1585
/* DSP 1 is a C6713 */
1586
boot_loader_write_mem32(pao, 0, HPIAL_ADDR, address);
1587
boot_loader_write_mem32(pao, 0, HPIAH_ADDR, address >> 16);
1588
1589
/* dummy read every 4 words for 6205 advisory 1.4.4 */
1590
boot_loader_read_mem32(pao, 0, 0);
1591
1592
boot_loader_write_mem32(pao, 0, HPIDL_ADDR, data);
1593
boot_loader_write_mem32(pao, 0, HPIDH_ADDR, data >> 16);
1594
1595
/* dummy read every 4 words for 6205 advisory 1.4.4 */
1596
boot_loader_read_mem32(pao, 0, 0);
1597
}
1598
}
1599
1600
static u16 boot_loader_config_emif(struct hpi_adapter_obj *pao, int dsp_index)
1601
{
1602
if (dsp_index == 0) {
1603
u32 setting;
1604
1605
/* DSP 0 is always C6205 */
1606
1607
/* Set the EMIF */
1608
/* memory map of C6205 */
1609
/* 00000000-0000FFFF 16Kx32 internal program */
1610
/* 00400000-00BFFFFF CE0 2Mx32 SDRAM running @ 100MHz */
1611
1612
/* EMIF config */
1613
/*------------ */
1614
/* Global EMIF control */
1615
boot_loader_write_mem32(pao, dsp_index, 0x01800000, 0x3779);
1616
#define WS_OFS 28
1617
#define WST_OFS 22
1618
#define WH_OFS 20
1619
#define RS_OFS 16
1620
#define RST_OFS 8
1621
#define MTYPE_OFS 4
1622
#define RH_OFS 0
1623
1624
/* EMIF CE0 setup - 2Mx32 Sync DRAM on ASI5000 cards only */
1625
setting = 0x00000030;
1626
boot_loader_write_mem32(pao, dsp_index, 0x01800008, setting);
1627
if (setting != boot_loader_read_mem32(pao, dsp_index,
1628
0x01800008))
1629
return HPI6205_ERROR_DSP_EMIF1;
1630
1631
/* EMIF CE1 setup - 32 bit async. This is 6713 #1 HPI, */
1632
/* which occupies D15..0. 6713 starts at 27MHz, so need */
1633
/* plenty of wait states. See dsn8701.rtf, and 6713 errata. */
1634
/* WST should be 71, but 63 is max possible */
1635
setting =
1636
(1L << WS_OFS) | (63L << WST_OFS) | (1L << WH_OFS) |
1637
(1L << RS_OFS) | (63L << RST_OFS) | (1L << RH_OFS) |
1638
(2L << MTYPE_OFS);
1639
boot_loader_write_mem32(pao, dsp_index, 0x01800004, setting);
1640
if (setting != boot_loader_read_mem32(pao, dsp_index,
1641
0x01800004))
1642
return HPI6205_ERROR_DSP_EMIF2;
1643
1644
/* EMIF CE2 setup - 32 bit async. This is 6713 #2 HPI, */
1645
/* which occupies D15..0. 6713 starts at 27MHz, so need */
1646
/* plenty of wait states */
1647
setting =
1648
(1L << WS_OFS) | (28L << WST_OFS) | (1L << WH_OFS) |
1649
(1L << RS_OFS) | (63L << RST_OFS) | (1L << RH_OFS) |
1650
(2L << MTYPE_OFS);
1651
boot_loader_write_mem32(pao, dsp_index, 0x01800010, setting);
1652
if (setting != boot_loader_read_mem32(pao, dsp_index,
1653
0x01800010))
1654
return HPI6205_ERROR_DSP_EMIF3;
1655
1656
/* EMIF CE3 setup - 32 bit async. */
1657
/* This is the PLD on the ASI5000 cards only */
1658
setting =
1659
(1L << WS_OFS) | (10L << WST_OFS) | (1L << WH_OFS) |
1660
(1L << RS_OFS) | (10L << RST_OFS) | (1L << RH_OFS) |
1661
(2L << MTYPE_OFS);
1662
boot_loader_write_mem32(pao, dsp_index, 0x01800014, setting);
1663
if (setting != boot_loader_read_mem32(pao, dsp_index,
1664
0x01800014))
1665
return HPI6205_ERROR_DSP_EMIF4;
1666
1667
/* set EMIF SDRAM control for 2Mx32 SDRAM (512x32x4 bank) */
1668
/* need to use this else DSP code crashes? */
1669
boot_loader_write_mem32(pao, dsp_index, 0x01800018,
1670
0x07117000);
1671
1672
/* EMIF SDRAM Refresh Timing */
1673
/* EMIF SDRAM timing (orig = 0x410, emulator = 0x61a) */
1674
boot_loader_write_mem32(pao, dsp_index, 0x0180001C,
1675
0x00000410);
1676
1677
} else if (dsp_index == 1) {
1678
/* test access to the C6713s HPI registers */
1679
u32 write_data = 0, read_data = 0, i = 0;
1680
1681
/* Set up HPIC for little endian, by setiing HPIC:HWOB=1 */
1682
write_data = 1;
1683
boot_loader_write_mem32(pao, 0, HPICL_ADDR, write_data);
1684
boot_loader_write_mem32(pao, 0, HPICH_ADDR, write_data);
1685
/* C67 HPI is on lower 16bits of 32bit EMIF */
1686
read_data =
1687
0xFFF7 & boot_loader_read_mem32(pao, 0, HPICL_ADDR);
1688
if (write_data != read_data) {
1689
HPI_DEBUG_LOG(ERROR, "HPICL %x %x\n", write_data,
1690
read_data);
1691
return HPI6205_ERROR_C6713_HPIC;
1692
}
1693
/* HPIA - walking ones test */
1694
write_data = 1;
1695
for (i = 0; i < 32; i++) {
1696
boot_loader_write_mem32(pao, 0, HPIAL_ADDR,
1697
write_data);
1698
boot_loader_write_mem32(pao, 0, HPIAH_ADDR,
1699
(write_data >> 16));
1700
read_data =
1701
0xFFFF & boot_loader_read_mem32(pao, 0,
1702
HPIAL_ADDR);
1703
read_data =
1704
read_data | ((0xFFFF &
1705
boot_loader_read_mem32(pao, 0,
1706
HPIAH_ADDR))
1707
<< 16);
1708
if (read_data != write_data) {
1709
HPI_DEBUG_LOG(ERROR, "HPIA %x %x\n",
1710
write_data, read_data);
1711
return HPI6205_ERROR_C6713_HPIA;
1712
}
1713
write_data = write_data << 1;
1714
}
1715
1716
/* setup C67x PLL
1717
* ** C6713 datasheet says we cannot program PLL from HPI,
1718
* and indeed if we try to set the PLL multiply from the HPI,
1719
* the PLL does not seem to lock, so we enable the PLL and
1720
* use the default multiply of x 7, which for a 27MHz clock
1721
* gives a DSP speed of 189MHz
1722
*/
1723
/* bypass PLL */
1724
boot_loader_write_mem32(pao, dsp_index, 0x01B7C100, 0x0000);
1725
hpios_delay_micro_seconds(1000);
1726
/* EMIF = 189/3=63MHz */
1727
boot_loader_write_mem32(pao, dsp_index, 0x01B7C120, 0x8002);
1728
/* peri = 189/2 */
1729
boot_loader_write_mem32(pao, dsp_index, 0x01B7C11C, 0x8001);
1730
/* cpu = 189/1 */
1731
boot_loader_write_mem32(pao, dsp_index, 0x01B7C118, 0x8000);
1732
hpios_delay_micro_seconds(1000);
1733
/* ** SGT test to take GPO3 high when we start the PLL */
1734
/* and low when the delay is completed */
1735
/* FSX0 <- '1' (GPO3) */
1736
boot_loader_write_mem32(pao, 0, (0x018C0024L), 0x00002A0A);
1737
/* PLL not bypassed */
1738
boot_loader_write_mem32(pao, dsp_index, 0x01B7C100, 0x0001);
1739
hpios_delay_micro_seconds(1000);
1740
/* FSX0 <- '0' (GPO3) */
1741
boot_loader_write_mem32(pao, 0, (0x018C0024L), 0x00002A02);
1742
1743
/* 6205 EMIF CE1 resetup - 32 bit async. */
1744
/* Now 6713 #1 is running at 189MHz can reduce waitstates */
1745
boot_loader_write_mem32(pao, 0, 0x01800004, /* CE1 */
1746
(1L << WS_OFS) | (8L << WST_OFS) | (1L << WH_OFS) |
1747
(1L << RS_OFS) | (12L << RST_OFS) | (1L << RH_OFS) |
1748
(2L << MTYPE_OFS));
1749
1750
hpios_delay_micro_seconds(1000);
1751
1752
/* check that we can read one of the PLL registers */
1753
/* PLL should not be bypassed! */
1754
if ((boot_loader_read_mem32(pao, dsp_index, 0x01B7C100) & 0xF)
1755
!= 0x0001) {
1756
return HPI6205_ERROR_C6713_PLL;
1757
}
1758
/* setup C67x EMIF (note this is the only use of
1759
BAR1 via BootLoader_WriteMem32) */
1760
boot_loader_write_mem32(pao, dsp_index, C6713_EMIF_GCTL,
1761
0x000034A8);
1762
1763
/* EMIF CE0 setup - 2Mx32 Sync DRAM
1764
31..28 Wr setup
1765
27..22 Wr strobe
1766
21..20 Wr hold
1767
19..16 Rd setup
1768
15..14 -
1769
13..8 Rd strobe
1770
7..4 MTYPE 0011 Sync DRAM 32bits
1771
3 Wr hold MSB
1772
2..0 Rd hold
1773
*/
1774
boot_loader_write_mem32(pao, dsp_index, C6713_EMIF_CE0,
1775
0x00000030);
1776
1777
/* EMIF SDRAM Extension
1778
0x00
1779
31-21 0000b 0000b 000b
1780
20 WR2RD = 2cycles-1 = 1b
1781
1782
19-18 WR2DEAC = 3cycle-1 = 10b
1783
17 WR2WR = 2cycle-1 = 1b
1784
16-15 R2WDQM = 4cycle-1 = 11b
1785
14-12 RD2WR = 6cycles-1 = 101b
1786
1787
11-10 RD2DEAC = 4cycle-1 = 11b
1788
9 RD2RD = 2cycle-1 = 1b
1789
8-7 THZP = 3cycle-1 = 10b
1790
6-5 TWR = 2cycle-1 = 01b (tWR = 17ns)
1791
4 TRRD = 2cycle = 0b (tRRD = 14ns)
1792
3-1 TRAS = 5cycle-1 = 100b (Tras=42ns)
1793
1 CAS latency = 3cyc = 1b
1794
(for Micron 2M32-7 operating at 100MHz)
1795
*/
1796
boot_loader_write_mem32(pao, dsp_index, C6713_EMIF_SDRAMEXT,
1797
0x001BDF29);
1798
1799
/* EMIF SDRAM control - set up for a 2Mx32 SDRAM (512x32x4 bank)
1800
31 - 0b -
1801
30 SDBSZ 1b 4 bank
1802
29..28 SDRSZ 00b 11 row address pins
1803
1804
27..26 SDCSZ 01b 8 column address pins
1805
25 RFEN 1b refersh enabled
1806
24 INIT 1b init SDRAM!
1807
1808
23..20 TRCD 0001b (Trcd/Tcyc)-1 = (20/10)-1 = 1
1809
1810
19..16 TRP 0001b (Trp/Tcyc)-1 = (20/10)-1 = 1
1811
1812
15..12 TRC 0110b (Trc/Tcyc)-1 = (70/10)-1 = 6
1813
1814
11..0 - 0000b 0000b 0000b
1815
*/
1816
boot_loader_write_mem32(pao, dsp_index, C6713_EMIF_SDRAMCTL,
1817
0x47116000);
1818
1819
/* SDRAM refresh timing
1820
Need 4,096 refresh cycles every 64ms = 15.625us = 1562cycles of 100MHz = 0x61A
1821
*/
1822
boot_loader_write_mem32(pao, dsp_index,
1823
C6713_EMIF_SDRAMTIMING, 0x00000410);
1824
1825
hpios_delay_micro_seconds(1000);
1826
} else if (dsp_index == 2) {
1827
/* DSP 2 is a C6713 */
1828
}
1829
1830
return 0;
1831
}
1832
1833
static u16 boot_loader_test_memory(struct hpi_adapter_obj *pao, int dsp_index,
1834
u32 start_address, u32 length)
1835
{
1836
u32 i = 0, j = 0;
1837
u32 test_addr = 0;
1838
u32 test_data = 0, data = 0;
1839
1840
length = 1000;
1841
1842
/* for 1st word, test each bit in the 32bit word, */
1843
/* dwLength specifies number of 32bit words to test */
1844
/*for(i=0; i<dwLength; i++) */
1845
i = 0;
1846
{
1847
test_addr = start_address + i * 4;
1848
test_data = 0x00000001;
1849
for (j = 0; j < 32; j++) {
1850
boot_loader_write_mem32(pao, dsp_index, test_addr,
1851
test_data);
1852
data = boot_loader_read_mem32(pao, dsp_index,
1853
test_addr);
1854
if (data != test_data) {
1855
HPI_DEBUG_LOG(VERBOSE,
1856
"Memtest error details "
1857
"%08x %08x %08x %i\n", test_addr,
1858
test_data, data, dsp_index);
1859
return 1; /* error */
1860
}
1861
test_data = test_data << 1;
1862
} /* for(j) */
1863
} /* for(i) */
1864
1865
/* for the next 100 locations test each location, leaving it as zero */
1866
/* write a zero to the next word in memory before we read */
1867
/* the previous write to make sure every memory location is unique */
1868
for (i = 0; i < 100; i++) {
1869
test_addr = start_address + i * 4;
1870
test_data = 0xA5A55A5A;
1871
boot_loader_write_mem32(pao, dsp_index, test_addr, test_data);
1872
boot_loader_write_mem32(pao, dsp_index, test_addr + 4, 0);
1873
data = boot_loader_read_mem32(pao, dsp_index, test_addr);
1874
if (data != test_data) {
1875
HPI_DEBUG_LOG(VERBOSE,
1876
"Memtest error details "
1877
"%08x %08x %08x %i\n", test_addr, test_data,
1878
data, dsp_index);
1879
return 1; /* error */
1880
}
1881
/* leave location as zero */
1882
boot_loader_write_mem32(pao, dsp_index, test_addr, 0x0);
1883
}
1884
1885
/* zero out entire memory block */
1886
for (i = 0; i < length; i++) {
1887
test_addr = start_address + i * 4;
1888
boot_loader_write_mem32(pao, dsp_index, test_addr, 0x0);
1889
}
1890
return 0;
1891
}
1892
1893
static u16 boot_loader_test_internal_memory(struct hpi_adapter_obj *pao,
1894
int dsp_index)
1895
{
1896
int err = 0;
1897
if (dsp_index == 0) {
1898
/* DSP 0 is a C6205 */
1899
/* 64K prog mem */
1900
err = boot_loader_test_memory(pao, dsp_index, 0x00000000,
1901
0x10000);
1902
if (!err)
1903
/* 64K data mem */
1904
err = boot_loader_test_memory(pao, dsp_index,
1905
0x80000000, 0x10000);
1906
} else if (dsp_index == 1) {
1907
/* DSP 1 is a C6713 */
1908
/* 192K internal mem */
1909
err = boot_loader_test_memory(pao, dsp_index, 0x00000000,
1910
0x30000);
1911
if (!err)
1912
/* 64K internal mem / L2 cache */
1913
err = boot_loader_test_memory(pao, dsp_index,
1914
0x00030000, 0x10000);
1915
}
1916
1917
if (err)
1918
return HPI6205_ERROR_DSP_INTMEM;
1919
else
1920
return 0;
1921
}
1922
1923
static u16 boot_loader_test_external_memory(struct hpi_adapter_obj *pao,
1924
int dsp_index)
1925
{
1926
u32 dRAM_start_address = 0;
1927
u32 dRAM_size = 0;
1928
1929
if (dsp_index == 0) {
1930
/* only test for SDRAM if an ASI5000 card */
1931
if (pao->pci.pci_dev->subsystem_device == 0x5000) {
1932
/* DSP 0 is always C6205 */
1933
dRAM_start_address = 0x00400000;
1934
dRAM_size = 0x200000;
1935
/*dwDRAMinc=1024; */
1936
} else
1937
return 0;
1938
} else if (dsp_index == 1) {
1939
/* DSP 1 is a C6713 */
1940
dRAM_start_address = 0x80000000;
1941
dRAM_size = 0x200000;
1942
/*dwDRAMinc=1024; */
1943
}
1944
1945
if (boot_loader_test_memory(pao, dsp_index, dRAM_start_address,
1946
dRAM_size))
1947
return HPI6205_ERROR_DSP_EXTMEM;
1948
return 0;
1949
}
1950
1951
static u16 boot_loader_test_pld(struct hpi_adapter_obj *pao, int dsp_index)
1952
{
1953
u32 data = 0;
1954
if (dsp_index == 0) {
1955
/* only test for DSP0 PLD on ASI5000 card */
1956
if (pao->pci.pci_dev->subsystem_device == 0x5000) {
1957
/* PLD is located at CE3=0x03000000 */
1958
data = boot_loader_read_mem32(pao, dsp_index,
1959
0x03000008);
1960
if ((data & 0xF) != 0x5)
1961
return HPI6205_ERROR_DSP_PLD;
1962
data = boot_loader_read_mem32(pao, dsp_index,
1963
0x0300000C);
1964
if ((data & 0xF) != 0xA)
1965
return HPI6205_ERROR_DSP_PLD;
1966
}
1967
} else if (dsp_index == 1) {
1968
/* DSP 1 is a C6713 */
1969
if (pao->pci.pci_dev->subsystem_device == 0x8700) {
1970
/* PLD is located at CE1=0x90000000 */
1971
data = boot_loader_read_mem32(pao, dsp_index,
1972
0x90000010);
1973
if ((data & 0xFF) != 0xAA)
1974
return HPI6205_ERROR_DSP_PLD;
1975
/* 8713 - LED on */
1976
boot_loader_write_mem32(pao, dsp_index, 0x90000000,
1977
0x02);
1978
}
1979
}
1980
return 0;
1981
}
1982
1983
/** Transfer data to or from DSP
1984
nOperation = H620_H620_HIF_SEND_DATA or H620_HIF_GET_DATA
1985
*/
1986
static short hpi6205_transfer_data(struct hpi_adapter_obj *pao, u8 *p_data,
1987
u32 data_size, int operation)
1988
{
1989
struct hpi_hw_obj *phw = pao->priv;
1990
u32 data_transferred = 0;
1991
u16 err = 0;
1992
u32 temp2;
1993
struct bus_master_interface *interface = phw->p_interface_buffer;
1994
1995
if (!p_data)
1996
return HPI_ERROR_INVALID_DATA_POINTER;
1997
1998
data_size &= ~3L; /* round data_size down to nearest 4 bytes */
1999
2000
/* make sure state is IDLE */
2001
if (!wait_dsp_ack(phw, H620_HIF_IDLE, HPI6205_TIMEOUT))
2002
return HPI_ERROR_DSP_HARDWARE;
2003
2004
while (data_transferred < data_size) {
2005
u32 this_copy = data_size - data_transferred;
2006
2007
if (this_copy > HPI6205_SIZEOF_DATA)
2008
this_copy = HPI6205_SIZEOF_DATA;
2009
2010
if (operation == H620_HIF_SEND_DATA)
2011
memcpy((void *)&interface->u.b_data[0],
2012
&p_data[data_transferred], this_copy);
2013
2014
interface->transfer_size_in_bytes = this_copy;
2015
2016
/* DSP must change this back to nOperation */
2017
interface->dsp_ack = H620_HIF_IDLE;
2018
send_dsp_command(phw, operation);
2019
2020
temp2 = wait_dsp_ack(phw, operation, HPI6205_TIMEOUT);
2021
HPI_DEBUG_LOG(DEBUG, "spun %d times for data xfer of %d\n",
2022
HPI6205_TIMEOUT - temp2, this_copy);
2023
2024
if (!temp2) {
2025
/* timed out */
2026
HPI_DEBUG_LOG(ERROR,
2027
"Timed out waiting for " "state %d got %d\n",
2028
operation, interface->dsp_ack);
2029
2030
break;
2031
}
2032
if (operation == H620_HIF_GET_DATA)
2033
memcpy(&p_data[data_transferred],
2034
(void *)&interface->u.b_data[0], this_copy);
2035
2036
data_transferred += this_copy;
2037
}
2038
if (interface->dsp_ack != operation)
2039
HPI_DEBUG_LOG(DEBUG, "interface->dsp_ack=%d, expected %d\n",
2040
interface->dsp_ack, operation);
2041
/* err=HPI_ERROR_DSP_HARDWARE; */
2042
2043
send_dsp_command(phw, H620_HIF_IDLE);
2044
2045
return err;
2046
}
2047
2048
/* wait for up to timeout_us microseconds for the DSP
2049
to signal state by DMA into dwDspAck
2050
*/
2051
static int wait_dsp_ack(struct hpi_hw_obj *phw, int state, int timeout_us)
2052
{
2053
struct bus_master_interface *interface = phw->p_interface_buffer;
2054
int t = timeout_us / 4;
2055
2056
rmb(); /* ensure interface->dsp_ack is up to date */
2057
while ((interface->dsp_ack != state) && --t) {
2058
hpios_delay_micro_seconds(4);
2059
rmb(); /* DSP changes dsp_ack by DMA */
2060
}
2061
2062
/*HPI_DEBUG_LOG(VERBOSE, "Spun %d for %d\n", timeout_us/4-t, state); */
2063
return t * 4;
2064
}
2065
2066
/* set the busmaster interface to cmd, then interrupt the DSP */
2067
static void send_dsp_command(struct hpi_hw_obj *phw, int cmd)
2068
{
2069
struct bus_master_interface *interface = phw->p_interface_buffer;
2070
u32 r;
2071
2072
interface->host_cmd = cmd;
2073
wmb(); /* DSP gets state by DMA, make sure it is written to memory */
2074
/* before we interrupt the DSP */
2075
r = ioread32(phw->prHDCR);
2076
r |= (u32)C6205_HDCR_DSPINT;
2077
iowrite32(r, phw->prHDCR);
2078
r &= ~(u32)C6205_HDCR_DSPINT;
2079
iowrite32(r, phw->prHDCR);
2080
}
2081
2082
static unsigned int message_count;
2083
2084
static u16 message_response_sequence(struct hpi_adapter_obj *pao,
2085
struct hpi_message *phm, struct hpi_response *phr)
2086
{
2087
u32 time_out, time_out2;
2088
struct hpi_hw_obj *phw = pao->priv;
2089
struct bus_master_interface *interface = phw->p_interface_buffer;
2090
u16 err = 0;
2091
2092
message_count++;
2093
if (phm->size > sizeof(interface->u.message_buffer)) {
2094
phr->error = HPI_ERROR_MESSAGE_BUFFER_TOO_SMALL;
2095
phr->specific_error = sizeof(interface->u.message_buffer);
2096
phr->size = sizeof(struct hpi_response_header);
2097
HPI_DEBUG_LOG(ERROR,
2098
"message len %d too big for buffer %zd \n", phm->size,
2099
sizeof(interface->u.message_buffer));
2100
return 0;
2101
}
2102
2103
/* Assume buffer of type struct bus_master_interface_62
2104
is allocated "noncacheable" */
2105
2106
if (!wait_dsp_ack(phw, H620_HIF_IDLE, HPI6205_TIMEOUT)) {
2107
HPI_DEBUG_LOG(DEBUG, "timeout waiting for idle\n");
2108
return HPI6205_ERROR_MSG_RESP_IDLE_TIMEOUT;
2109
}
2110
2111
memcpy(&interface->u.message_buffer, phm, phm->size);
2112
/* signal we want a response */
2113
send_dsp_command(phw, H620_HIF_GET_RESP);
2114
2115
time_out2 = wait_dsp_ack(phw, H620_HIF_GET_RESP, HPI6205_TIMEOUT);
2116
2117
if (!time_out2) {
2118
HPI_DEBUG_LOG(ERROR,
2119
"(%u) Timed out waiting for " "GET_RESP state [%x]\n",
2120
message_count, interface->dsp_ack);
2121
} else {
2122
HPI_DEBUG_LOG(VERBOSE,
2123
"(%u) transition to GET_RESP after %u\n",
2124
message_count, HPI6205_TIMEOUT - time_out2);
2125
}
2126
/* spin waiting on HIF interrupt flag (end of msg process) */
2127
time_out = HPI6205_TIMEOUT;
2128
2129
/* read the result */
2130
if (time_out) {
2131
if (interface->u.response_buffer.response.size <= phr->size)
2132
memcpy(phr, &interface->u.response_buffer,
2133
interface->u.response_buffer.response.size);
2134
else {
2135
HPI_DEBUG_LOG(ERROR,
2136
"response len %d too big for buffer %d\n",
2137
interface->u.response_buffer.response.size,
2138
phr->size);
2139
memcpy(phr, &interface->u.response_buffer,
2140
sizeof(struct hpi_response_header));
2141
phr->error = HPI_ERROR_RESPONSE_BUFFER_TOO_SMALL;
2142
phr->specific_error =
2143
interface->u.response_buffer.response.size;
2144
phr->size = sizeof(struct hpi_response_header);
2145
}
2146
}
2147
/* set interface back to idle */
2148
send_dsp_command(phw, H620_HIF_IDLE);
2149
2150
if (!time_out || !time_out2) {
2151
HPI_DEBUG_LOG(DEBUG, "something timed out!\n");
2152
return HPI6205_ERROR_MSG_RESP_TIMEOUT;
2153
}
2154
/* special case for adapter close - */
2155
/* wait for the DSP to indicate it is idle */
2156
if (phm->function == HPI_ADAPTER_CLOSE) {
2157
if (!wait_dsp_ack(phw, H620_HIF_IDLE, HPI6205_TIMEOUT)) {
2158
HPI_DEBUG_LOG(DEBUG,
2159
"Timeout waiting for idle "
2160
"(on adapter_close)\n");
2161
return HPI6205_ERROR_MSG_RESP_IDLE_TIMEOUT;
2162
}
2163
}
2164
err = hpi_validate_response(phm, phr);
2165
return err;
2166
}
2167
2168
static void hw_message(struct hpi_adapter_obj *pao, struct hpi_message *phm,
2169
struct hpi_response *phr)
2170
{
2171
2172
u16 err = 0;
2173
2174
hpios_dsplock_lock(pao);
2175
2176
err = message_response_sequence(pao, phm, phr);
2177
2178
/* maybe an error response */
2179
if (err) {
2180
/* something failed in the HPI/DSP interface */
2181
if (err >= HPI_ERROR_BACKEND_BASE) {
2182
phr->error = HPI_ERROR_DSP_COMMUNICATION;
2183
phr->specific_error = err;
2184
} else {
2185
phr->error = err;
2186
}
2187
2188
pao->dsp_crashed++;
2189
2190
/* just the header of the response is valid */
2191
phr->size = sizeof(struct hpi_response_header);
2192
goto err;
2193
} else
2194
pao->dsp_crashed = 0;
2195
2196
if (phr->error != 0) /* something failed in the DSP */
2197
goto err;
2198
2199
switch (phm->function) {
2200
case HPI_OSTREAM_WRITE:
2201
case HPI_ISTREAM_ANC_WRITE:
2202
err = hpi6205_transfer_data(pao, phm->u.d.u.data.pb_data,
2203
phm->u.d.u.data.data_size, H620_HIF_SEND_DATA);
2204
break;
2205
2206
case HPI_ISTREAM_READ:
2207
case HPI_OSTREAM_ANC_READ:
2208
err = hpi6205_transfer_data(pao, phm->u.d.u.data.pb_data,
2209
phm->u.d.u.data.data_size, H620_HIF_GET_DATA);
2210
break;
2211
2212
}
2213
phr->error = err;
2214
2215
err:
2216
hpios_dsplock_unlock(pao);
2217
2218
return;
2219
}
2220
2221