aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorNicolin Chen <nicoleotsuka@gmail.com>2017-12-17 21:52:02 -0500
committerMark Brown <broonie@kernel.org>2017-12-19 04:24:31 -0500
commit7a8fceb74de407f65201f3eaaee35377c2b71dbb (patch)
tree3a57b19afc0188ab92b0bdcc0aeb763cb56fadb1
parent8483c06797b62dbddac800b555b2fa1c689dbb1c (diff)
ASoC: fsl_ssi: Refine all comments
This patch refines the comments by: 1) Removing all out-of-date comments 2) Removing all not-so-useful comments 3) Unifying the styles of all comments 4) Shortening comments to be more conise 5) Adding comments to improve code readablity 6) Moving all register related comments to fsl_ssi.h 7) Adding comments to all register and field defines Signed-off-by: Nicolin Chen <nicoleotsuka@gmail.com> Tested-by: Maciej S. Szmigiero <mail@maciej.szmigiero.name> Reviewed-by: Maciej S. Szmigiero <mail@maciej.szmigiero.name> Acked-by: Timur Tabi <timur@tabi.org> Signed-off-by: Mark Brown <broonie@kernel.org>
-rw-r--r--sound/soc/fsl/fsl_ssi.c383
-rw-r--r--sound/soc/fsl/fsl_ssi.h67
-rw-r--r--sound/soc/fsl/fsl_ssi_dbg.c12
3 files changed, 208 insertions, 254 deletions
diff --git a/sound/soc/fsl/fsl_ssi.c b/sound/soc/fsl/fsl_ssi.c
index e903c92d5512..ff1827a074be 100644
--- a/sound/soc/fsl/fsl_ssi.c
+++ b/sound/soc/fsl/fsl_ssi.c
@@ -187,42 +187,48 @@ struct fsl_ssi_soc_data {
187/** 187/**
188 * fsl_ssi: per-SSI private data 188 * fsl_ssi: per-SSI private data
189 * 189 *
190 * @reg: Pointer to the regmap registers 190 * @regs: Pointer to the regmap registers
191 * @irq: IRQ of this SSI 191 * @irq: IRQ of this SSI
192 * @cpu_dai_drv: CPU DAI driver for this device 192 * @cpu_dai_drv: CPU DAI driver for this device
193 * 193 *
194 * @dai_fmt: DAI configuration this device is currently used with 194 * @dai_fmt: DAI configuration this device is currently used with
195 * @i2s_mode: i2s and network mode configuration of the device. Is used to 195 * @i2s_mode: I2S and Network mode configuration of SCR register
196 * switch between normal and i2s/network mode
197 * mode depending on the number of channels
198 * @use_dma: DMA is used or FIQ with stream filter 196 * @use_dma: DMA is used or FIQ with stream filter
199 * @use_dual_fifo: DMA with support for both FIFOs used 197 * @use_dual_fifo: DMA with support for dual FIFO mode
200 * @fifo_deph: Depth of the SSI FIFOs 198 * @has_ipg_clk_name: If "ipg" is in the clock name list of device tree
201 * @slot_width: width of each DAI slot 199 * @fifo_depth: Depth of the SSI FIFOs
202 * @slots: number of slots 200 * @slot_width: Width of each DAI slot
203 * @rxtx_reg_val: Specific register settings for receive/transmit configuration 201 * @slots: Number of slots
202 * @rxtx_reg_val: Specific RX/TX register settings
204 * 203 *
205 * @clk: SSI clock 204 * @clk: Clock source to access register
206 * @baudclk: SSI baud clock for master mode 205 * @baudclk: Clock source to generate bit and frame-sync clocks
207 * @baudclk_streams: Active streams that are using baudclk 206 * @baudclk_streams: Active streams that are using baudclk
208 * 207 *
208 * @regcache_sfcsr: Cache sfcsr register value during suspend and resume
209 * @regcache_sacnt: Cache sacnt register value during suspend and resume
210 *
209 * @dma_params_tx: DMA transmit parameters 211 * @dma_params_tx: DMA transmit parameters
210 * @dma_params_rx: DMA receive parameters 212 * @dma_params_rx: DMA receive parameters
211 * @ssi_phys: physical address of the SSI registers 213 * @ssi_phys: physical address of the SSI registers
212 * 214 *
213 * @fiq_params: FIQ stream filtering parameters 215 * @fiq_params: FIQ stream filtering parameters
214 * 216 *
215 * @pdev: Pointer to pdev used for deprecated fsl-ssi sound card 217 * @pdev: Pointer to pdev when using fsl-ssi as sound card (ppc only)
218 * TODO: Should be replaced with simple-sound-card
216 * 219 *
217 * @dbg_stats: Debugging statistics 220 * @dbg_stats: Debugging statistics
218 * 221 *
219 * @soc: SoC specific data 222 * @soc: SoC specific data
223 * @dev: Pointer to &pdev->dev
224 *
225 * @fifo_watermark: The FIFO watermark setting. Notifies DMA when there are
226 * @fifo_watermark or fewer words in TX fifo or
227 * @fifo_watermark or more empty words in RX fifo.
228 * @dma_maxburst: Max number of words to transfer in one go. So far,
229 * this is always the same as fifo_watermark.
220 * 230 *
221 * @fifo_watermark: the FIFO watermark setting. Notifies DMA when 231 * @ac97_reg_lock: Mutex lock to serialize AC97 register access operations
222 * there are @fifo_watermark or fewer words in TX fifo or
223 * @fifo_watermark or more empty words in RX fifo.
224 * @dma_maxburst: max number of words to transfer in one go. So far,
225 * this is always the same as fifo_watermark.
226 */ 232 */
227struct fsl_ssi { 233struct fsl_ssi {
228 struct regmap *regs; 234 struct regmap *regs;
@@ -243,20 +249,15 @@ struct fsl_ssi {
243 struct clk *baudclk; 249 struct clk *baudclk;
244 unsigned int baudclk_streams; 250 unsigned int baudclk_streams;
245 251
246 /* regcache for volatile regs */
247 u32 regcache_sfcsr; 252 u32 regcache_sfcsr;
248 u32 regcache_sacnt; 253 u32 regcache_sacnt;
249 254
250 /* DMA params */
251 struct snd_dmaengine_dai_dma_data dma_params_tx; 255 struct snd_dmaengine_dai_dma_data dma_params_tx;
252 struct snd_dmaengine_dai_dma_data dma_params_rx; 256 struct snd_dmaengine_dai_dma_data dma_params_rx;
253 dma_addr_t ssi_phys; 257 dma_addr_t ssi_phys;
254 258
255 /* params for non-dma FIQ stream filtered mode */
256 struct imx_pcm_fiq_params fiq_params; 259 struct imx_pcm_fiq_params fiq_params;
257 260
258 /* Used when using fsl-ssi as sound-card. This is only used by ppc and
259 * should be replaced with simple-sound-card. */
260 struct platform_device *pdev; 261 struct platform_device *pdev;
261 262
262 struct fsl_ssi_dbg dbg_stats; 263 struct fsl_ssi_dbg dbg_stats;
@@ -271,19 +272,19 @@ struct fsl_ssi {
271}; 272};
272 273
273/* 274/*
274 * imx51 and later SoCs have a slightly different IP that allows the 275 * SoC specific data
275 * SSI configuration while the SSI unit is running.
276 *
277 * More important, it is necessary on those SoCs to configure the
278 * sperate TX/RX DMA bits just before starting the stream
279 * (fsl_ssi_trigger). The SDMA unit has to be configured before fsl_ssi
280 * sends any DMA requests to the SDMA unit, otherwise it is not defined
281 * how the SDMA unit handles the DMA request.
282 * 276 *
283 * SDMA units are present on devices starting at imx35 but the imx35 277 * Notes:
284 * reference manual states that the DMA bits should not be changed 278 * 1) SSI in earlier SoCS has critical bits in control registers that
285 * while the SSI unit is running (SSIEN). So we support the necessary 279 * cannot be changed after SSI starts running -- a software reset
286 * online configuration of fsl-ssi starting at imx51. 280 * (set SSIEN to 0) is required to change their values. So adding
281 * an offline_config flag for these SoCs.
282 * 2) SDMA is available since imx35. However, imx35 does not support
283 * DMA bits changing when SSI is running, so set offline_config.
284 * 3) imx51 and later versions support register configurations when
285 * SSI is running (SSIEN); For these versions, DMA needs to be
286 * configured before SSI sends DMA request to avoid an undefined
287 * DMA request on the SDMA side.
287 */ 288 */
288 289
289static struct fsl_ssi_soc_data fsl_ssi_mpc8610 = { 290static struct fsl_ssi_soc_data fsl_ssi_mpc8610 = {
@@ -342,17 +343,9 @@ static bool fsl_ssi_is_i2s_cbm_cfs(struct fsl_ssi *ssi)
342 return (ssi->dai_fmt & SND_SOC_DAIFMT_MASTER_MASK) == 343 return (ssi->dai_fmt & SND_SOC_DAIFMT_MASTER_MASK) ==
343 SND_SOC_DAIFMT_CBM_CFS; 344 SND_SOC_DAIFMT_CBM_CFS;
344} 345}
346
345/** 347/**
346 * fsl_ssi_isr: SSI interrupt handler 348 * Interrupt handler to gather states
347 *
348 * Although it's possible to use the interrupt handler to send and receive
349 * data to/from the SSI, we use the DMA instead. Programming is more
350 * complicated, but the performance is much better.
351 *
352 * This interrupt handler is used only to gather statistics.
353 *
354 * @irq: IRQ of the SSI device
355 * @dev_id: pointer to the fsl_ssi structure for this SSI device
356 */ 349 */
357static irqreturn_t fsl_ssi_isr(int irq, void *dev_id) 350static irqreturn_t fsl_ssi_isr(int irq, void *dev_id)
358{ 351{
@@ -361,10 +354,6 @@ static irqreturn_t fsl_ssi_isr(int irq, void *dev_id)
361 __be32 sisr; 354 __be32 sisr;
362 __be32 sisr2; 355 __be32 sisr2;
363 356
364 /* We got an interrupt, so read the status register to see what we
365 were interrupted for. We mask it with the Interrupt Enable register
366 so that we only check for events that we're interested in.
367 */
368 regmap_read(regs, CCSR_SSI_SISR, &sisr); 357 regmap_read(regs, CCSR_SSI_SISR, &sisr);
369 358
370 sisr2 = sisr & ssi->soc->sisr_write_mask; 359 sisr2 = sisr & ssi->soc->sisr_write_mask;
@@ -377,8 +366,8 @@ static irqreturn_t fsl_ssi_isr(int irq, void *dev_id)
377 return IRQ_HANDLED; 366 return IRQ_HANDLED;
378} 367}
379 368
380/* 369/**
381 * Enable/Disable all rx/tx config flags at once. 370 * Enable or disable all rx/tx config flags at once
382 */ 371 */
383static void fsl_ssi_rxtx_config(struct fsl_ssi *ssi, bool enable) 372static void fsl_ssi_rxtx_config(struct fsl_ssi *ssi, bool enable)
384{ 373{
@@ -405,13 +394,8 @@ static void fsl_ssi_rxtx_config(struct fsl_ssi *ssi, bool enable)
405 } 394 }
406} 395}
407 396
408/* 397/**
409 * Clear RX or TX FIFO to remove samples from the previous 398 * Clear remaining data in the FIFO to avoid dirty data or channel slipping
410 * stream session which may be still present in the FIFO and
411 * may introduce bad samples and/or channel slipping.
412 *
413 * Note: The SOR is not documented in recent IMX datasheet, but
414 * is described in IMX51 reference manual at section 56.3.3.15.
415 */ 399 */
416static void fsl_ssi_fifo_clear(struct fsl_ssi *ssi, bool is_rx) 400static void fsl_ssi_fifo_clear(struct fsl_ssi *ssi, bool is_rx)
417{ 401{
@@ -424,7 +408,7 @@ static void fsl_ssi_fifo_clear(struct fsl_ssi *ssi, bool is_rx)
424 } 408 }
425} 409}
426 410
427/* 411/**
428 * Calculate the bits that have to be disabled for the current stream that is 412 * Calculate the bits that have to be disabled for the current stream that is
429 * getting disabled. This keeps the bits enabled that are necessary for the 413 * getting disabled. This keeps the bits enabled that are necessary for the
430 * second stream to work if 'stream_active' is true. 414 * second stream to work if 'stream_active' is true.
@@ -444,9 +428,8 @@ static void fsl_ssi_fifo_clear(struct fsl_ssi *ssi, bool is_rx)
444 ((vals_disable) & \ 428 ((vals_disable) & \
445 ((vals_disable) ^ ((vals_stream) * (u32)!!(stream_active)))) 429 ((vals_disable) ^ ((vals_stream) * (u32)!!(stream_active))))
446 430
447/* 431/**
448 * Enable/Disable a ssi configuration. You have to pass either 432 * Enable or disable SSI configuration.
449 * ssi->rxtx_reg_val.rx or tx as vals parameter.
450 */ 433 */
451static void fsl_ssi_config(struct fsl_ssi *ssi, bool enable, 434static void fsl_ssi_config(struct fsl_ssi *ssi, bool enable,
452 struct fsl_ssi_reg_val *vals) 435 struct fsl_ssi_reg_val *vals)
@@ -467,24 +450,28 @@ static void fsl_ssi_config(struct fsl_ssi *ssi, bool enable,
467 else 450 else
468 keep_active = 0; 451 keep_active = 0;
469 452
470 /* Find the other direction values rx or tx which we do not want to 453 /* Get the opposite direction to keep its values untouched */
471 * modify */
472 if (&ssi->rxtx_reg_val.rx == vals) 454 if (&ssi->rxtx_reg_val.rx == vals)
473 avals = &ssi->rxtx_reg_val.tx; 455 avals = &ssi->rxtx_reg_val.tx;
474 else 456 else
475 avals = &ssi->rxtx_reg_val.rx; 457 avals = &ssi->rxtx_reg_val.rx;
476 458
477 /* If vals should be disabled, start with disabling the unit */
478 if (!enable) { 459 if (!enable) {
460 /*
461 * To keep the other stream safe, exclude shared bits between
462 * both streams, and get safe bits to disable current stream
463 */
479 u32 scr = fsl_ssi_disable_val(vals->scr, avals->scr, 464 u32 scr = fsl_ssi_disable_val(vals->scr, avals->scr,
480 keep_active); 465 keep_active);
466 /* Safely disable SCR register for the stream */
481 regmap_update_bits(regs, CCSR_SSI_SCR, scr, 0); 467 regmap_update_bits(regs, CCSR_SSI_SCR, scr, 0);
482 } 468 }
483 469
484 /* 470 /*
485 * We are running on a SoC which does not support online SSI 471 * For cases where online configuration is not supported,
486 * reconfiguration, so we have to enable all necessary flags at once 472 * 1) Enable all necessary bits of both streams when 1st stream starts
487 * even if we do not use them later (capture and playback configuration) 473 * even if the opposite stream will not start
474 * 2) Disable all remaining bits of both streams when last stream ends
488 */ 475 */
489 if (ssi->soc->offline_config) { 476 if (ssi->soc->offline_config) {
490 if ((enable && !nr_active_streams) || 477 if ((enable && !nr_active_streams) ||
@@ -494,10 +481,7 @@ static void fsl_ssi_config(struct fsl_ssi *ssi, bool enable,
494 goto config_done; 481 goto config_done;
495 } 482 }
496 483
497 /* 484 /* Online configure single direction while SSI is running */
498 * Configure single direction units while the SSI unit is running
499 * (online configuration)
500 */
501 if (enable) { 485 if (enable) {
502 fsl_ssi_fifo_clear(ssi, vals->scr & CCSR_SSI_SCR_RE); 486 fsl_ssi_fifo_clear(ssi, vals->scr & CCSR_SSI_SCR_RE);
503 487
@@ -510,15 +494,9 @@ static void fsl_ssi_config(struct fsl_ssi *ssi, bool enable,
510 u32 stcr; 494 u32 stcr;
511 495
512 /* 496 /*
513 * Disabling the necessary flags for one of rx/tx while the 497 * To keep the other stream safe, exclude shared bits between
514 * other stream is active is a little bit more difficult. We 498 * both streams, and get safe bits to disable current stream
515 * have to disable only those flags that differ between both
516 * streams (rx XOR tx) and that are set in the stream that is
517 * disabled now. Otherwise we could alter flags of the other
518 * stream
519 */ 499 */
520
521 /* These assignments are simply vals without bits set in avals*/
522 sier = fsl_ssi_disable_val(vals->sier, avals->sier, 500 sier = fsl_ssi_disable_val(vals->sier, avals->sier,
523 keep_active); 501 keep_active);
524 srcr = fsl_ssi_disable_val(vals->srcr, avals->srcr, 502 srcr = fsl_ssi_disable_val(vals->srcr, avals->srcr,
@@ -526,6 +504,7 @@ static void fsl_ssi_config(struct fsl_ssi *ssi, bool enable,
526 stcr = fsl_ssi_disable_val(vals->stcr, avals->stcr, 504 stcr = fsl_ssi_disable_val(vals->stcr, avals->stcr,
527 keep_active); 505 keep_active);
528 506
507 /* Safely disable other control registers for the stream */
529 regmap_update_bits(regs, CCSR_SSI_SRCR, srcr, 0); 508 regmap_update_bits(regs, CCSR_SSI_SRCR, srcr, 0);
530 regmap_update_bits(regs, CCSR_SSI_STCR, stcr, 0); 509 regmap_update_bits(regs, CCSR_SSI_STCR, stcr, 0);
531 regmap_update_bits(regs, CCSR_SSI_SIER, sier, 0); 510 regmap_update_bits(regs, CCSR_SSI_SIER, sier, 0);
@@ -534,26 +513,21 @@ static void fsl_ssi_config(struct fsl_ssi *ssi, bool enable,
534config_done: 513config_done:
535 /* Enabling of subunits is done after configuration */ 514 /* Enabling of subunits is done after configuration */
536 if (enable) { 515 if (enable) {
516 /*
517 * Start DMA before setting TE to avoid FIFO underrun
518 * which may cause a channel slip or a channel swap
519 *
520 * TODO: FIQ cases might also need this upon testing
521 */
537 if (ssi->use_dma && (vals->scr & CCSR_SSI_SCR_TE)) { 522 if (ssi->use_dma && (vals->scr & CCSR_SSI_SCR_TE)) {
538 /*
539 * Be sure the Tx FIFO is filled when TE is set.
540 * Otherwise, there are some chances to start the
541 * playback with some void samples inserted first,
542 * generating a channel slip.
543 *
544 * First, SSIEN must be set, to let the FIFO be filled.
545 *
546 * Notes:
547 * - Limit this fix to the DMA case until FIQ cases can
548 * be tested.
549 * - Limit the length of the busy loop to not lock the
550 * system too long, even if 1-2 loops are sufficient
551 * in general.
552 */
553 int i; 523 int i;
554 int max_loop = 100; 524 int max_loop = 100;
525
526 /* Enable SSI first to send TX DMA request */
555 regmap_update_bits(regs, CCSR_SSI_SCR, 527 regmap_update_bits(regs, CCSR_SSI_SCR,
556 CCSR_SSI_SCR_SSIEN, CCSR_SSI_SCR_SSIEN); 528 CCSR_SSI_SCR_SSIEN, CCSR_SSI_SCR_SSIEN);
529
530 /* Busy wait until TX FIFO not empty -- DMA working */
557 for (i = 0; i < max_loop; i++) { 531 for (i = 0; i < max_loop; i++) {
558 u32 sfcsr; 532 u32 sfcsr;
559 regmap_read(regs, CCSR_SSI_SFCSR, &sfcsr); 533 regmap_read(regs, CCSR_SSI_SFCSR, &sfcsr);
@@ -565,6 +539,7 @@ config_done:
565 "Timeout waiting TX FIFO filling\n"); 539 "Timeout waiting TX FIFO filling\n");
566 } 540 }
567 } 541 }
542 /* Enable all remaining bits */
568 regmap_update_bits(regs, CCSR_SSI_SCR, vals->scr, vals->scr); 543 regmap_update_bits(regs, CCSR_SSI_SCR, vals->scr, vals->scr);
569 } 544 }
570} 545}
@@ -581,20 +556,9 @@ static void fsl_ssi_tx_ac97_saccst_setup(struct fsl_ssi *ssi)
581 556
582 /* no SACC{ST,EN,DIS} regs on imx21-class SSI */ 557 /* no SACC{ST,EN,DIS} regs on imx21-class SSI */
583 if (!ssi->soc->imx21regs) { 558 if (!ssi->soc->imx21regs) {
584 /* 559 /* Disable all channel slots */
585 * Note that these below aren't just normal registers.
586 * They are a way to disable or enable bits in SACCST
587 * register:
588 * - writing a '1' bit at some position in SACCEN sets the
589 * relevant bit in SACCST,
590 * - writing a '1' bit at some position in SACCDIS unsets
591 * the relevant bit in SACCST register.
592 *
593 * The two writes below first disable all channels slots,
594 * then enable just slots 3 & 4 ("PCM Playback Left Channel"
595 * and "PCM Playback Right Channel").
596 */
597 regmap_write(regs, CCSR_SSI_SACCDIS, 0xff); 560 regmap_write(regs, CCSR_SSI_SACCDIS, 0xff);
561 /* Enable slots 3 & 4 -- PCM Playback Left & Right channels */
598 regmap_write(regs, CCSR_SSI_SACCEN, 0x300); 562 regmap_write(regs, CCSR_SSI_SACCEN, 0x300);
599 } 563 }
600} 564}
@@ -602,23 +566,11 @@ static void fsl_ssi_tx_ac97_saccst_setup(struct fsl_ssi *ssi)
602static void fsl_ssi_tx_config(struct fsl_ssi *ssi, bool enable) 566static void fsl_ssi_tx_config(struct fsl_ssi *ssi, bool enable)
603{ 567{
604 /* 568 /*
605 * Why are we setting up SACCST everytime we are starting a 569 * SACCST might be modified via AC Link by a CODEC if it sends
606 * playback? 570 * extra bits in their SLOTREQ requests, which'll accidentally
607 * Some CODECs (like VT1613 CODEC on UDOO board) like to 571 * send valid data to slots other than normal playback slots.
608 * (sometimes) set extra bits in their SLOTREQ requests.
609 * When a bit is set in a SLOTREQ request then SSI sets the
610 * relevant bit in SACCST automatically (it is enough if a bit was
611 * set in a SLOTREQ just once, bits in SACCST are 'sticky').
612 * If an extra slot gets enabled that's a disaster for playback
613 * because some of normal left or right channel samples are
614 * redirected instead to this extra slot.
615 * 572 *
616 * A workaround implemented in fsl-asoc-card of setting an 573 * To be safe, configure SACCST right before TX starts.
617 * appropriate CODEC register so that slots 3 & 4 (the normal
618 * stereo playback slots) are used for S/PDIF seems to mostly fix
619 * this issue on the UDOO board but since this CODEC is so
620 * untrustworthy let's play safe here and make sure that no extra
621 * slots are enabled every time a playback is started.
622 */ 574 */
623 if (enable && fsl_ssi_is_ac97(ssi)) 575 if (enable && fsl_ssi_is_ac97(ssi))
624 fsl_ssi_tx_ac97_saccst_setup(ssi); 576 fsl_ssi_tx_ac97_saccst_setup(ssi);
@@ -626,10 +578,8 @@ static void fsl_ssi_tx_config(struct fsl_ssi *ssi, bool enable)
626 fsl_ssi_config(ssi, enable, &ssi->rxtx_reg_val.tx); 578 fsl_ssi_config(ssi, enable, &ssi->rxtx_reg_val.tx);
627} 579}
628 580
629/* 581/**
630 * Setup rx/tx register values used to enable/disable the streams. These will 582 * Cache critical bits of SIER, SRCR, STCR and SCR to later set them safely
631 * be used later in fsl_ssi_config to setup the streams without the need to
632 * check for all different SSI modes.
633 */ 583 */
634static void fsl_ssi_setup_reg_vals(struct fsl_ssi *ssi) 584static void fsl_ssi_setup_reg_vals(struct fsl_ssi *ssi)
635{ 585{
@@ -642,6 +592,7 @@ static void fsl_ssi_setup_reg_vals(struct fsl_ssi *ssi)
642 reg->tx.stcr = CCSR_SSI_STCR_TFEN0; 592 reg->tx.stcr = CCSR_SSI_STCR_TFEN0;
643 reg->tx.scr = 0; 593 reg->tx.scr = 0;
644 594
595 /* AC97 has already enabled SSIEN, RE and TE, so ignore them */
645 if (!fsl_ssi_is_ac97(ssi)) { 596 if (!fsl_ssi_is_ac97(ssi)) {
646 reg->rx.scr = CCSR_SSI_SCR_SSIEN | CCSR_SSI_SCR_RE; 597 reg->rx.scr = CCSR_SSI_SCR_SSIEN | CCSR_SSI_SCR_RE;
647 reg->tx.scr = CCSR_SSI_SCR_SSIEN | CCSR_SSI_SCR_TE; 598 reg->tx.scr = CCSR_SSI_SCR_SSIEN | CCSR_SSI_SCR_TE;
@@ -663,24 +614,17 @@ static void fsl_ssi_setup_ac97(struct fsl_ssi *ssi)
663{ 614{
664 struct regmap *regs = ssi->regs; 615 struct regmap *regs = ssi->regs;
665 616
666 /* 617 /* Setup the clock control register */
667 * Setup the clock control register
668 */
669 regmap_write(regs, CCSR_SSI_STCCR, 618 regmap_write(regs, CCSR_SSI_STCCR,
670 CCSR_SSI_SxCCR_WL(17) | CCSR_SSI_SxCCR_DC(13)); 619 CCSR_SSI_SxCCR_WL(17) | CCSR_SSI_SxCCR_DC(13));
671 regmap_write(regs, CCSR_SSI_SRCCR, 620 regmap_write(regs, CCSR_SSI_SRCCR,
672 CCSR_SSI_SxCCR_WL(17) | CCSR_SSI_SxCCR_DC(13)); 621 CCSR_SSI_SxCCR_WL(17) | CCSR_SSI_SxCCR_DC(13));
673 622
674 /* 623 /* Enable AC97 mode and startup the SSI */
675 * Enable AC97 mode and startup the SSI
676 */
677 regmap_write(regs, CCSR_SSI_SACNT, 624 regmap_write(regs, CCSR_SSI_SACNT,
678 CCSR_SSI_SACNT_AC97EN | CCSR_SSI_SACNT_FV); 625 CCSR_SSI_SACNT_AC97EN | CCSR_SSI_SACNT_FV);
679 626
680 /* 627 /* AC97 has to communicate with codec before starting a stream */
681 * Enable SSI, Transmit and Receive. AC97 has to communicate with the
682 * codec before a stream is started.
683 */
684 regmap_update_bits(regs, CCSR_SSI_SCR, 628 regmap_update_bits(regs, CCSR_SSI_SCR,
685 CCSR_SSI_SCR_SSIEN | CCSR_SSI_SCR_TE | CCSR_SSI_SCR_RE, 629 CCSR_SSI_SCR_SSIEN | CCSR_SSI_SCR_TE | CCSR_SSI_SCR_RE,
686 CCSR_SSI_SCR_SSIEN | CCSR_SSI_SCR_TE | CCSR_SSI_SCR_RE); 630 CCSR_SSI_SCR_SSIEN | CCSR_SSI_SCR_TE | CCSR_SSI_SCR_RE);
@@ -688,14 +632,6 @@ static void fsl_ssi_setup_ac97(struct fsl_ssi *ssi)
688 regmap_write(regs, CCSR_SSI_SOR, CCSR_SSI_SOR_WAIT(3)); 632 regmap_write(regs, CCSR_SSI_SOR, CCSR_SSI_SOR_WAIT(3));
689} 633}
690 634
691/**
692 * fsl_ssi_startup: create a new substream
693 *
694 * This is the first function called when a stream is opened.
695 *
696 * If this is the first stream open, then grab the IRQ and program most of
697 * the SSI registers.
698 */
699static int fsl_ssi_startup(struct snd_pcm_substream *substream, 635static int fsl_ssi_startup(struct snd_pcm_substream *substream,
700 struct snd_soc_dai *dai) 636 struct snd_soc_dai *dai)
701{ 637{
@@ -707,7 +643,8 @@ static int fsl_ssi_startup(struct snd_pcm_substream *substream,
707 if (ret) 643 if (ret)
708 return ret; 644 return ret;
709 645
710 /* When using dual fifo mode, it is safer to ensure an even period 646 /*
647 * When using dual fifo mode, it is safer to ensure an even period
711 * size. If appearing to an odd number while DMA always starts its 648 * size. If appearing to an odd number while DMA always starts its
712 * task from fifo0, fifo1 would be neglected at the end of each 649 * task from fifo0, fifo1 would be neglected at the end of each
713 * period. But SSI would still access fifo1 with an invalid data. 650 * period. But SSI would still access fifo1 with an invalid data.
@@ -719,10 +656,6 @@ static int fsl_ssi_startup(struct snd_pcm_substream *substream,
719 return 0; 656 return 0;
720} 657}
721 658
722/**
723 * fsl_ssi_shutdown: shutdown the SSI
724 *
725 */
726static void fsl_ssi_shutdown(struct snd_pcm_substream *substream, 659static void fsl_ssi_shutdown(struct snd_pcm_substream *substream,
727 struct snd_soc_dai *dai) 660 struct snd_soc_dai *dai)
728{ 661{
@@ -734,7 +667,7 @@ static void fsl_ssi_shutdown(struct snd_pcm_substream *substream,
734} 667}
735 668
736/** 669/**
737 * fsl_ssi_set_bclk - configure Digital Audio Interface bit clock 670 * Configure Digital Audio Interface bit clock
738 * 671 *
739 * Note: This function can be only called when using SSI as DAI master 672 * Note: This function can be only called when using SSI as DAI master
740 * 673 *
@@ -851,17 +784,15 @@ static int fsl_ssi_set_bclk(struct snd_pcm_substream *substream,
851} 784}
852 785
853/** 786/**
854 * fsl_ssi_hw_params - program the sample size 787 * Configure SSI based on PCM hardware parameters
855 *
856 * Most of the SSI registers have been programmed in the startup function,
857 * but the word length must be programmed here. Unfortunately, programming
858 * the SxCCR.WL bits requires the SSI to be temporarily disabled. This can
859 * cause a problem with supporting simultaneous playback and capture. If
860 * the SSI is already playing a stream, then that stream may be temporarily
861 * stopped when you start capture.
862 * 788 *
863 * Note: The SxCCR.DC and SxCCR.PM bits are only used if the SSI is the 789 * Notes:
864 * clock master. 790 * 1) SxCCR.WL bits are critical bits that require SSI to be temporarily
791 * disabled on offline_config SoCs. Even for online configurable SoCs
792 * running in synchronous mode (both TX and RX use STCCR), it is not
793 * safe to re-configure them when both two streams start running.
794 * 2) SxCCR.PM, SxCCR.DIV2 and SxCCR.PSR bits will be configured in the
795 * fsl_ssi_set_bclk() if SSI is the DAI clock master.
865 */ 796 */
866static int fsl_ssi_hw_params(struct snd_pcm_substream *substream, 797static int fsl_ssi_hw_params(struct snd_pcm_substream *substream,
867 struct snd_pcm_hw_params *hw_params, struct snd_soc_dai *cpu_dai) 798 struct snd_pcm_hw_params *hw_params, struct snd_soc_dai *cpu_dai)
@@ -879,8 +810,10 @@ static int fsl_ssi_hw_params(struct snd_pcm_substream *substream,
879 enabled = scr_val & CCSR_SSI_SCR_SSIEN; 810 enabled = scr_val & CCSR_SSI_SCR_SSIEN;
880 811
881 /* 812 /*
882 * If we're in synchronous mode, and the SSI is already enabled, 813 * SSI is properly configured if it is enabled and running in
883 * then STCCR is already set properly. 814 * the synchronous mode; Note that AC97 mode is an exception
815 * that should set separate configurations for STCCR and SRCCR
816 * despite running in the synchronous mode.
884 */ 817 */
885 if (enabled && ssi->cpu_dai_drv.symmetric_rates) 818 if (enabled && ssi->cpu_dai_drv.symmetric_rates)
886 return 0; 819 return 0;
@@ -902,10 +835,7 @@ static int fsl_ssi_hw_params(struct snd_pcm_substream *substream,
902 835
903 if (!fsl_ssi_is_ac97(ssi)) { 836 if (!fsl_ssi_is_ac97(ssi)) {
904 u8 i2smode; 837 u8 i2smode;
905 /* 838 /* Normal + Network mode to send 16-bit data in 32-bit frames */
906 * Switch to normal net mode in order to have a frame sync
907 * signal every 32 bits instead of 16 bits
908 */
909 if (fsl_ssi_is_i2s_cbm_cfs(ssi) && sample_size == 16) 839 if (fsl_ssi_is_i2s_cbm_cfs(ssi) && sample_size == 16)
910 i2smode = CCSR_SSI_SCR_I2S_MODE_NORMAL | 840 i2smode = CCSR_SSI_SCR_I2S_MODE_NORMAL |
911 CCSR_SSI_SCR_NET; 841 CCSR_SSI_SCR_NET;
@@ -917,16 +847,6 @@ static int fsl_ssi_hw_params(struct snd_pcm_substream *substream,
917 channels == 1 ? 0 : i2smode); 847 channels == 1 ? 0 : i2smode);
918 } 848 }
919 849
920 /*
921 * FIXME: The documentation says that SxCCR[WL] should not be
922 * modified while the SSI is enabled. The only time this can
923 * happen is if we're trying to do simultaneous playback and
924 * capture in asynchronous mode. Unfortunately, I have been enable
925 * to get that to work at all on the P1022DS. Therefore, we don't
926 * bother to disable/enable the SSI when setting SxCCR[WL], because
927 * the SSI will stop anyway. Maybe one day, this will get fixed.
928 */
929
930 /* In synchronous mode, the SSI uses STCCR for capture */ 850 /* In synchronous mode, the SSI uses STCCR for capture */
931 if ((substream->stream == SNDRV_PCM_STREAM_PLAYBACK) || 851 if ((substream->stream == SNDRV_PCM_STREAM_PLAYBACK) ||
932 ssi->cpu_dai_drv.symmetric_rates) 852 ssi->cpu_dai_drv.symmetric_rates)
@@ -972,6 +892,7 @@ static int _fsl_ssi_set_dai_fmt(struct device *dev,
972 892
973 regmap_read(regs, CCSR_SSI_SCR, &scr); 893 regmap_read(regs, CCSR_SSI_SCR, &scr);
974 scr &= ~(CCSR_SSI_SCR_SYN | CCSR_SSI_SCR_I2S_MODE_MASK); 894 scr &= ~(CCSR_SSI_SCR_SYN | CCSR_SSI_SCR_I2S_MODE_MASK);
895 /* Synchronize frame sync clock for TE to avoid data slipping */
975 scr |= CCSR_SSI_SCR_SYNC_TX_FS; 896 scr |= CCSR_SSI_SCR_SYNC_TX_FS;
976 897
977 mask = CCSR_SSI_STCR_TXBIT0 | CCSR_SSI_STCR_TFDIR | CCSR_SSI_STCR_TXDIR | 898 mask = CCSR_SSI_STCR_TXBIT0 | CCSR_SSI_STCR_TFDIR | CCSR_SSI_STCR_TXDIR |
@@ -982,6 +903,7 @@ static int _fsl_ssi_set_dai_fmt(struct device *dev,
982 stcr &= ~mask; 903 stcr &= ~mask;
983 srcr &= ~mask; 904 srcr &= ~mask;
984 905
906 /* Use Network mode as default */
985 ssi->i2s_mode = CCSR_SSI_SCR_NET; 907 ssi->i2s_mode = CCSR_SSI_SCR_NET;
986 switch (fmt & SND_SOC_DAIFMT_FORMAT_MASK) { 908 switch (fmt & SND_SOC_DAIFMT_FORMAT_MASK) {
987 case SND_SOC_DAIFMT_I2S: 909 case SND_SOC_DAIFMT_I2S:
@@ -1022,6 +944,7 @@ static int _fsl_ssi_set_dai_fmt(struct device *dev,
1022 CCSR_SSI_STCR_TXBIT0; 944 CCSR_SSI_STCR_TXBIT0;
1023 break; 945 break;
1024 case SND_SOC_DAIFMT_AC97: 946 case SND_SOC_DAIFMT_AC97:
947 /* Data on falling edge of bclk, frame high, 1clk before data */
1025 ssi->i2s_mode |= CCSR_SSI_SCR_I2S_MODE_NORMAL; 948 ssi->i2s_mode |= CCSR_SSI_SCR_I2S_MODE_NORMAL;
1026 break; 949 break;
1027 default: 950 default:
@@ -1054,13 +977,16 @@ static int _fsl_ssi_set_dai_fmt(struct device *dev,
1054 /* DAI clock master masks */ 977 /* DAI clock master masks */
1055 switch (fmt & SND_SOC_DAIFMT_MASTER_MASK) { 978 switch (fmt & SND_SOC_DAIFMT_MASTER_MASK) {
1056 case SND_SOC_DAIFMT_CBS_CFS: 979 case SND_SOC_DAIFMT_CBS_CFS:
980 /* Output bit and frame sync clocks */
1057 strcr |= CCSR_SSI_STCR_TFDIR | CCSR_SSI_STCR_TXDIR; 981 strcr |= CCSR_SSI_STCR_TFDIR | CCSR_SSI_STCR_TXDIR;
1058 scr |= CCSR_SSI_SCR_SYS_CLK_EN; 982 scr |= CCSR_SSI_SCR_SYS_CLK_EN;
1059 break; 983 break;
1060 case SND_SOC_DAIFMT_CBM_CFM: 984 case SND_SOC_DAIFMT_CBM_CFM:
985 /* Input bit or frame sync clocks */
1061 scr &= ~CCSR_SSI_SCR_SYS_CLK_EN; 986 scr &= ~CCSR_SSI_SCR_SYS_CLK_EN;
1062 break; 987 break;
1063 case SND_SOC_DAIFMT_CBM_CFS: 988 case SND_SOC_DAIFMT_CBM_CFS:
989 /* Input bit clock but output frame sync clock */
1064 strcr &= ~CCSR_SSI_STCR_TXDIR; 990 strcr &= ~CCSR_SSI_STCR_TXDIR;
1065 strcr |= CCSR_SSI_STCR_TFDIR; 991 strcr |= CCSR_SSI_STCR_TFDIR;
1066 scr &= ~CCSR_SSI_SCR_SYS_CLK_EN; 992 scr &= ~CCSR_SSI_SCR_SYS_CLK_EN;
@@ -1073,8 +999,8 @@ static int _fsl_ssi_set_dai_fmt(struct device *dev,
1073 stcr |= strcr; 999 stcr |= strcr;
1074 srcr |= strcr; 1000 srcr |= strcr;
1075 1001
1002 /* Set SYN mode and clear RXDIR bit when using SYN or AC97 mode */
1076 if (ssi->cpu_dai_drv.symmetric_rates || fsl_ssi_is_ac97(ssi)) { 1003 if (ssi->cpu_dai_drv.symmetric_rates || fsl_ssi_is_ac97(ssi)) {
1077 /* Need to clear RXDIR when using SYNC or AC97 mode */
1078 srcr &= ~CCSR_SSI_SRCR_RXDIR; 1004 srcr &= ~CCSR_SSI_SRCR_RXDIR;
1079 scr |= CCSR_SSI_SCR_SYN; 1005 scr |= CCSR_SSI_SCR_SYN;
1080 } 1006 }
@@ -1106,12 +1032,13 @@ static int _fsl_ssi_set_dai_fmt(struct device *dev,
1106} 1032}
1107 1033
1108/** 1034/**
1109 * fsl_ssi_set_dai_fmt - configure Digital Audio Interface Format. 1035 * Configure Digital Audio Interface (DAI) Format
1110 */ 1036 */
1111static int fsl_ssi_set_dai_fmt(struct snd_soc_dai *cpu_dai, unsigned int fmt) 1037static int fsl_ssi_set_dai_fmt(struct snd_soc_dai *cpu_dai, unsigned int fmt)
1112{ 1038{
1113 struct fsl_ssi *ssi = snd_soc_dai_get_drvdata(cpu_dai); 1039 struct fsl_ssi *ssi = snd_soc_dai_get_drvdata(cpu_dai);
1114 1040
1041 /* AC97 configured DAIFMT earlier in the probe() */
1115 if (fsl_ssi_is_ac97(ssi)) 1042 if (fsl_ssi_is_ac97(ssi))
1116 return 0; 1043 return 0;
1117 1044
@@ -1119,9 +1046,7 @@ static int fsl_ssi_set_dai_fmt(struct snd_soc_dai *cpu_dai, unsigned int fmt)
1119} 1046}
1120 1047
1121/** 1048/**
1122 * fsl_ssi_set_dai_tdm_slot - set TDM slot number 1049 * Set TDM slot number and slot width
1123 *
1124 * Note: This function can be only called when using SSI as DAI master
1125 */ 1050 */
1126static int fsl_ssi_set_dai_tdm_slot(struct snd_soc_dai *cpu_dai, u32 tx_mask, 1051static int fsl_ssi_set_dai_tdm_slot(struct snd_soc_dai *cpu_dai, u32 tx_mask,
1127 u32 rx_mask, int slots, int slot_width) 1052 u32 rx_mask, int slots, int slot_width)
@@ -1149,17 +1074,17 @@ static int fsl_ssi_set_dai_tdm_slot(struct snd_soc_dai *cpu_dai, u32 tx_mask,
1149 regmap_update_bits(regs, CCSR_SSI_SRCCR, CCSR_SSI_SxCCR_DC_MASK, 1074 regmap_update_bits(regs, CCSR_SSI_SRCCR, CCSR_SSI_SxCCR_DC_MASK,
1150 CCSR_SSI_SxCCR_DC(slots)); 1075 CCSR_SSI_SxCCR_DC(slots));
1151 1076
1152 /* The register SxMSKs needs SSI to provide essential clock due to 1077 /* Save SSIEN bit of the SCR register */
1153 * hardware design. So we here temporarily enable SSI to set them.
1154 */
1155 regmap_read(regs, CCSR_SSI_SCR, &val); 1078 regmap_read(regs, CCSR_SSI_SCR, &val);
1156 val &= CCSR_SSI_SCR_SSIEN; 1079 val &= CCSR_SSI_SCR_SSIEN;
1080 /* Temporarily enable SSI to allow SxMSKs to be configurable */
1157 regmap_update_bits(regs, CCSR_SSI_SCR, CCSR_SSI_SCR_SSIEN, 1081 regmap_update_bits(regs, CCSR_SSI_SCR, CCSR_SSI_SCR_SSIEN,
1158 CCSR_SSI_SCR_SSIEN); 1082 CCSR_SSI_SCR_SSIEN);
1159 1083
1160 regmap_write(regs, CCSR_SSI_STMSK, ~tx_mask); 1084 regmap_write(regs, CCSR_SSI_STMSK, ~tx_mask);
1161 regmap_write(regs, CCSR_SSI_SRMSK, ~rx_mask); 1085 regmap_write(regs, CCSR_SSI_SRMSK, ~rx_mask);
1162 1086
1087 /* Restore the value of SSIEN bit */
1163 regmap_update_bits(regs, CCSR_SSI_SCR, CCSR_SSI_SCR_SSIEN, val); 1088 regmap_update_bits(regs, CCSR_SSI_SCR, CCSR_SSI_SCR_SSIEN, val);
1164 1089
1165 ssi->slot_width = slot_width; 1090 ssi->slot_width = slot_width;
@@ -1169,10 +1094,7 @@ static int fsl_ssi_set_dai_tdm_slot(struct snd_soc_dai *cpu_dai, u32 tx_mask,
1169} 1094}
1170 1095
1171/** 1096/**
1172 * fsl_ssi_trigger: start and stop the DMA transfer. 1097 * Start or stop SSI and corresponding DMA transaction.
1173 *
1174 * This function is called by ALSA to start, stop, pause, and resume the DMA
1175 * transfer of data.
1176 * 1098 *
1177 * The DMA channel is in external master start and pause mode, which 1099 * The DMA channel is in external master start and pause mode, which
1178 * means the SSI completely controls the flow of data. 1100 * means the SSI completely controls the flow of data.
@@ -1207,6 +1129,7 @@ static int fsl_ssi_trigger(struct snd_pcm_substream *substream, int cmd,
1207 return -EINVAL; 1129 return -EINVAL;
1208 } 1130 }
1209 1131
1132 /* Clear corresponding FIFO */
1210 if (fsl_ssi_is_ac97(ssi)) { 1133 if (fsl_ssi_is_ac97(ssi)) {
1211 if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) 1134 if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK)
1212 regmap_write(regs, CCSR_SSI_SOR, CCSR_SSI_SOR_TX_CLR); 1135 regmap_write(regs, CCSR_SSI_SOR, CCSR_SSI_SOR_TX_CLR);
@@ -1239,7 +1162,6 @@ static const struct snd_soc_dai_ops fsl_ssi_dai_ops = {
1239 .trigger = fsl_ssi_trigger, 1162 .trigger = fsl_ssi_trigger,
1240}; 1163};
1241 1164
1242/* Template for the CPU dai driver structure */
1243static struct snd_soc_dai_driver fsl_ssi_dai_template = { 1165static struct snd_soc_dai_driver fsl_ssi_dai_template = {
1244 .probe = fsl_ssi_dai_probe, 1166 .probe = fsl_ssi_dai_probe,
1245 .playback = { 1167 .playback = {
@@ -1383,6 +1305,7 @@ static int fsl_ssi_imx_probe(struct platform_device *pdev,
1383 u32 dmas[4]; 1305 u32 dmas[4];
1384 int ret; 1306 int ret;
1385 1307
1308 /* Backward compatible for a DT without ipg clock name assigned */
1386 if (ssi->has_ipg_clk_name) 1309 if (ssi->has_ipg_clk_name)
1387 ssi->clk = devm_clk_get(dev, "ipg"); 1310 ssi->clk = devm_clk_get(dev, "ipg");
1388 else 1311 else
@@ -1393,6 +1316,7 @@ static int fsl_ssi_imx_probe(struct platform_device *pdev,
1393 return ret; 1316 return ret;
1394 } 1317 }
1395 1318
1319 /* Enable the clock since regmap will not handle it in this case */
1396 if (!ssi->has_ipg_clk_name) { 1320 if (!ssi->has_ipg_clk_name) {
1397 ret = clk_prepare_enable(ssi->clk); 1321 ret = clk_prepare_enable(ssi->clk);
1398 if (ret) { 1322 if (ret) {
@@ -1401,9 +1325,7 @@ static int fsl_ssi_imx_probe(struct platform_device *pdev,
1401 } 1325 }
1402 } 1326 }
1403 1327
1404 /* For those SLAVE implementations, we ignore non-baudclk cases 1328 /* Do not error out for slave cases that live without a baud clock */
1405 * and, instead, abandon MASTER mode that needs baud clock.
1406 */
1407 ssi->baudclk = devm_clk_get(dev, "baud"); 1329 ssi->baudclk = devm_clk_get(dev, "baud");
1408 if (IS_ERR(ssi->baudclk)) 1330 if (IS_ERR(ssi->baudclk))
1409 dev_dbg(dev, "could not get baud clock: %ld\n", 1331 dev_dbg(dev, "could not get baud clock: %ld\n",
@@ -1414,25 +1336,23 @@ static int fsl_ssi_imx_probe(struct platform_device *pdev,
1414 ssi->dma_params_tx.addr = ssi->ssi_phys + CCSR_SSI_STX0; 1336 ssi->dma_params_tx.addr = ssi->ssi_phys + CCSR_SSI_STX0;
1415 ssi->dma_params_rx.addr = ssi->ssi_phys + CCSR_SSI_SRX0; 1337 ssi->dma_params_rx.addr = ssi->ssi_phys + CCSR_SSI_SRX0;
1416 1338
1339 /* Set to dual FIFO mode according to the SDMA sciprt */
1417 ret = of_property_read_u32_array(np, "dmas", dmas, 4); 1340 ret = of_property_read_u32_array(np, "dmas", dmas, 4);
1418 if (ssi->use_dma && !ret && dmas[2] == IMX_DMATYPE_SSI_DUAL) { 1341 if (ssi->use_dma && !ret && dmas[2] == IMX_DMATYPE_SSI_DUAL) {
1419 ssi->use_dual_fifo = true; 1342 ssi->use_dual_fifo = true;
1420 /* When using dual fifo mode, we need to keep watermark 1343 /*
1421 * as even numbers due to dma script limitation. 1344 * Use even numbers to avoid channel swap due to SDMA
1345 * script design
1422 */ 1346 */
1423 ssi->dma_params_tx.maxburst &= ~0x1; 1347 ssi->dma_params_tx.maxburst &= ~0x1;
1424 ssi->dma_params_rx.maxburst &= ~0x1; 1348 ssi->dma_params_rx.maxburst &= ~0x1;
1425 } 1349 }
1426 1350
1427 if (!ssi->use_dma) { 1351 if (!ssi->use_dma) {
1428
1429 /* 1352 /*
1430 * Some boards use an incompatible codec. To get it 1353 * Some boards use an incompatible codec. Use imx-fiq-pcm-audio
1431 * working, we are using imx-fiq-pcm-audio, that 1354 * to get it working, as DMA is not possible in this situation.
1432 * can handle those codecs. DMA is not possible in this
1433 * situation.
1434 */ 1355 */
1435
1436 ssi->fiq_params.irq = ssi->irq; 1356 ssi->fiq_params.irq = ssi->irq;
1437 ssi->fiq_params.base = iomem; 1357 ssi->fiq_params.base = iomem;
1438 ssi->fiq_params.dma_params_rx = &ssi->dma_params_rx; 1358 ssi->fiq_params.dma_params_rx = &ssi->dma_params_rx;
@@ -1490,12 +1410,14 @@ static int fsl_ssi_probe(struct platform_device *pdev)
1490 ssi->soc = of_id->data; 1410 ssi->soc = of_id->data;
1491 ssi->dev = dev; 1411 ssi->dev = dev;
1492 1412
1413 /* Check if being used in AC97 mode */
1493 sprop = of_get_property(np, "fsl,mode", NULL); 1414 sprop = of_get_property(np, "fsl,mode", NULL);
1494 if (sprop) { 1415 if (sprop) {
1495 if (!strcmp(sprop, "ac97-slave")) 1416 if (!strcmp(sprop, "ac97-slave"))
1496 ssi->dai_fmt = SND_SOC_DAIFMT_AC97; 1417 ssi->dai_fmt = SND_SOC_DAIFMT_AC97;
1497 } 1418 }
1498 1419
1420 /* Select DMA or FIQ */
1499 ssi->use_dma = !of_property_read_bool(np, "fsl,fiq-stream-filter"); 1421 ssi->use_dma = !of_property_read_bool(np, "fsl,fiq-stream-filter");
1500 1422
1501 if (fsl_ssi_is_ac97(ssi)) { 1423 if (fsl_ssi_is_ac97(ssi)) {
@@ -1504,7 +1426,6 @@ static int fsl_ssi_probe(struct platform_device *pdev)
1504 1426
1505 fsl_ac97_data = ssi; 1427 fsl_ac97_data = ssi;
1506 } else { 1428 } else {
1507 /* Initialize this copy of the CPU DAI driver structure */
1508 memcpy(&ssi->cpu_dai_drv, &fsl_ssi_dai_template, 1429 memcpy(&ssi->cpu_dai_drv, &fsl_ssi_dai_template,
1509 sizeof(fsl_ssi_dai_template)); 1430 sizeof(fsl_ssi_dai_template));
1510 } 1431 }
@@ -1517,10 +1438,7 @@ static int fsl_ssi_probe(struct platform_device *pdev)
1517 ssi->ssi_phys = res->start; 1438 ssi->ssi_phys = res->start;
1518 1439
1519 if (ssi->soc->imx21regs) { 1440 if (ssi->soc->imx21regs) {
1520 /* 1441 /* No SACC{ST,EN,DIS} regs in imx21-class SSI */
1521 * According to datasheet imx21-class SSI
1522 * don't have SACC{ST,EN,DIS} regs.
1523 */
1524 regconfig.max_register = CCSR_SSI_SRMSK; 1442 regconfig.max_register = CCSR_SSI_SRMSK;
1525 regconfig.num_reg_defaults_raw = 1443 regconfig.num_reg_defaults_raw =
1526 CCSR_SSI_SRMSK / sizeof(uint32_t) + 1; 1444 CCSR_SSI_SRMSK / sizeof(uint32_t) + 1;
@@ -1546,7 +1464,7 @@ static int fsl_ssi_probe(struct platform_device *pdev)
1546 return ssi->irq; 1464 return ssi->irq;
1547 } 1465 }
1548 1466
1549 /* Are the RX and the TX clocks locked? */ 1467 /* Set software limitations for synchronous mode */
1550 if (!of_find_property(np, "fsl,ssi-asynchronous", NULL)) { 1468 if (!of_find_property(np, "fsl,ssi-asynchronous", NULL)) {
1551 if (!fsl_ssi_is_ac97(ssi)) { 1469 if (!fsl_ssi_is_ac97(ssi)) {
1552 ssi->cpu_dai_drv.symmetric_rates = 1; 1470 ssi->cpu_dai_drv.symmetric_rates = 1;
@@ -1556,50 +1474,35 @@ static int fsl_ssi_probe(struct platform_device *pdev)
1556 ssi->cpu_dai_drv.symmetric_channels = 1; 1474 ssi->cpu_dai_drv.symmetric_channels = 1;
1557 } 1475 }
1558 1476
1559 /* Determine the FIFO depth. */ 1477 /* Fetch FIFO depth; Set to 8 for older DT without this property */
1560 iprop = of_get_property(np, "fsl,fifo-depth", NULL); 1478 iprop = of_get_property(np, "fsl,fifo-depth", NULL);
1561 if (iprop) 1479 if (iprop)
1562 ssi->fifo_depth = be32_to_cpup(iprop); 1480 ssi->fifo_depth = be32_to_cpup(iprop);
1563 else 1481 else
1564 /* Older 8610 DTs didn't have the fifo-depth property */
1565 ssi->fifo_depth = 8; 1482 ssi->fifo_depth = 8;
1566 1483
1567 /* 1484 /*
1568 * Set the watermark for transmit FIFO 0 and receive FIFO 0. We don't 1485 * Configure TX and RX DMA watermarks -- when to send a DMA request
1569 * use FIFO 1 but set the watermark appropriately nontheless.
1570 * We program the transmit water to signal a DMA transfer
1571 * if there are N elements left in the FIFO. For chips with 15-deep
1572 * FIFOs, set watermark to 8. This allows the SSI to operate at a
1573 * high data rate without channel slipping. Behavior is unchanged
1574 * for the older chips with a fifo depth of only 8. A value of 4
1575 * might be appropriate for the older chips, but is left at
1576 * fifo_depth-2 until sombody has a chance to test.
1577 * 1486 *
1578 * We set the watermark on the same level as the DMA burstsize. For 1487 * Values should be tested to avoid FIFO under/over run. Set maxburst
1579 * fiq it is probably better to use the biggest possible watermark 1488 * to fifo_watermark to maxiumize DMA transaction to reduce overhead.
1580 * size.
1581 */ 1489 */
1582 switch (ssi->fifo_depth) { 1490 switch (ssi->fifo_depth) {
1583 case 15: 1491 case 15:
1584 /* 1492 /*
1585 * 2 samples is not enough when running at high data 1493 * Set to 8 as a balanced configuration -- When TX FIFO has 8
1586 * rates (like 48kHz @ 16 bits/channel, 16 channels) 1494 * empty slots, send a DMA request to fill these 8 slots. The
1587 * 8 seems to split things evenly and leave enough time 1495 * remaining 7 slots should be able to allow DMA to finish the
1588 * for the DMA to fill the FIFO before it's over/under 1496 * transaction before TX FIFO underruns; Same applies to RX.
1589 * run. 1497 *
1498 * Tested with cases running at 48kHz @ 16 bits x 16 channels
1590 */ 1499 */
1591 ssi->fifo_watermark = 8; 1500 ssi->fifo_watermark = 8;
1592 ssi->dma_maxburst = 8; 1501 ssi->dma_maxburst = 8;
1593 break; 1502 break;
1594 case 8: 1503 case 8:
1595 default: 1504 default:
1596 /* 1505 /* Safely use old watermark configurations for older chips */
1597 * maintain old behavior for older chips.
1598 * Keeping it the same because I don't have an older
1599 * board to test with.
1600 * I suspect this could be changed to be something to
1601 * leave some more space in the fifo.
1602 */
1603 ssi->fifo_watermark = ssi->fifo_depth - 2; 1506 ssi->fifo_watermark = ssi->fifo_depth - 2;
1604 ssi->dma_maxburst = ssi->fifo_depth - 2; 1507 ssi->dma_maxburst = ssi->fifo_depth - 2;
1605 break; 1508 break;
@@ -1642,18 +1545,14 @@ static int fsl_ssi_probe(struct platform_device *pdev)
1642 if (ret) 1545 if (ret)
1643 goto error_asoc_register; 1546 goto error_asoc_register;
1644 1547
1645 /* 1548 /* Bypass it if using newer DT bindings of ASoC machine drivers */
1646 * If codec-handle property is missing from SSI node, we assume
1647 * that the machine driver uses new binding which does not require
1648 * SSI driver to trigger machine driver's probe.
1649 */
1650 if (!of_get_property(np, "codec-handle", NULL)) 1549 if (!of_get_property(np, "codec-handle", NULL))
1651 goto done; 1550 goto done;
1652 1551
1653 /* Trigger the machine driver's probe function. The platform driver 1552 /*
1654 * name of the machine driver is taken from /compatible property of the 1553 * Backward compatible for older bindings by manually triggering the
1655 * device tree. We also pass the address of the CPU DAI driver 1554 * machine driver's probe(). Use /compatible property, including the
1656 * structure. 1555 * address of CPU DAI driver structure, as the name of machine driver.
1657 */ 1556 */
1658 sprop = of_get_property(of_find_node_by_path("/"), "compatible", NULL); 1557 sprop = of_get_property(of_find_node_by_path("/"), "compatible", NULL);
1659 /* Sometimes the compatible name has a "fsl," prefix, so we strip it. */ 1558 /* Sometimes the compatible name has a "fsl," prefix, so we strip it. */
diff --git a/sound/soc/fsl/fsl_ssi.h b/sound/soc/fsl/fsl_ssi.h
index 506510540d0a..1ad3bde7f065 100644
--- a/sound/soc/fsl/fsl_ssi.h
+++ b/sound/soc/fsl/fsl_ssi.h
@@ -1,5 +1,5 @@
1/* 1/*
2 * fsl_ssi.h - ALSA SSI interface for the Freescale MPC8610 SoC 2 * fsl_ssi.h - ALSA SSI interface for the Freescale MPC8610 and i.MX SoC
3 * 3 *
4 * Author: Timur Tabi <timur@freescale.com> 4 * Author: Timur Tabi <timur@freescale.com>
5 * 5 *
@@ -12,31 +12,75 @@
12#ifndef _MPC8610_I2S_H 12#ifndef _MPC8610_I2S_H
13#define _MPC8610_I2S_H 13#define _MPC8610_I2S_H
14 14
15/* SSI registers */ 15/* -- SSI Register Map -- */
16
17/* SSI Transmit Data Register 0 */
16#define CCSR_SSI_STX0 0x00 18#define CCSR_SSI_STX0 0x00
19/* SSI Transmit Data Register 1 */
17#define CCSR_SSI_STX1 0x04 20#define CCSR_SSI_STX1 0x04
21/* SSI Receive Data Register 0 */
18#define CCSR_SSI_SRX0 0x08 22#define CCSR_SSI_SRX0 0x08
23/* SSI Receive Data Register 1 */
19#define CCSR_SSI_SRX1 0x0c 24#define CCSR_SSI_SRX1 0x0c
25/* SSI Control Register */
20#define CCSR_SSI_SCR 0x10 26#define CCSR_SSI_SCR 0x10
27/* SSI Interrupt Status Register */
21#define CCSR_SSI_SISR 0x14 28#define CCSR_SSI_SISR 0x14
29/* SSI Interrupt Enable Register */
22#define CCSR_SSI_SIER 0x18 30#define CCSR_SSI_SIER 0x18
31/* SSI Transmit Configuration Register */
23#define CCSR_SSI_STCR 0x1c 32#define CCSR_SSI_STCR 0x1c
33/* SSI Receive Configuration Register */
24#define CCSR_SSI_SRCR 0x20 34#define CCSR_SSI_SRCR 0x20
35/* SSI Transmit Clock Control Register */
25#define CCSR_SSI_STCCR 0x24 36#define CCSR_SSI_STCCR 0x24
37/* SSI Receive Clock Control Register */
26#define CCSR_SSI_SRCCR 0x28 38#define CCSR_SSI_SRCCR 0x28
39/* SSI FIFO Control/Status Register */
27#define CCSR_SSI_SFCSR 0x2c 40#define CCSR_SSI_SFCSR 0x2c
41/*
42 * SSI Test Register (Intended for debugging purposes only)
43 *
44 * Note: STR is not documented in recent IMX datasheet, but
45 * is described in IMX51 reference manual at section 56.3.3.14
46 */
28#define CCSR_SSI_STR 0x30 47#define CCSR_SSI_STR 0x30
48/*
49 * SSI Option Register (Intended for internal use only)
50 *
51 * Note: SOR is not documented in recent IMX datasheet, but
52 * is described in IMX51 reference manual at section 56.3.3.15
53 */
29#define CCSR_SSI_SOR 0x34 54#define CCSR_SSI_SOR 0x34
55/* SSI AC97 Control Register */
30#define CCSR_SSI_SACNT 0x38 56#define CCSR_SSI_SACNT 0x38
57/* SSI AC97 Command Address Register */
31#define CCSR_SSI_SACADD 0x3c 58#define CCSR_SSI_SACADD 0x3c
59/* SSI AC97 Command Data Register */
32#define CCSR_SSI_SACDAT 0x40 60#define CCSR_SSI_SACDAT 0x40
61/* SSI AC97 Tag Register */
33#define CCSR_SSI_SATAG 0x44 62#define CCSR_SSI_SATAG 0x44
63/* SSI Transmit Time Slot Mask Register */
34#define CCSR_SSI_STMSK 0x48 64#define CCSR_SSI_STMSK 0x48
65/* SSI Receive Time Slot Mask Register */
35#define CCSR_SSI_SRMSK 0x4c 66#define CCSR_SSI_SRMSK 0x4c
67/*
68 * SSI AC97 Channel Status Register
69 *
70 * The status could be changed by:
71 * 1) Writing a '1' bit at some position in SACCEN sets relevant bit in SACCST
72 * 2) Writing a '1' bit at some position in SACCDIS unsets the relevant bit
73 * 3) Receivng a '1' in SLOTREQ bit from external CODEC via AC Link
74 */
36#define CCSR_SSI_SACCST 0x50 75#define CCSR_SSI_SACCST 0x50
76/* SSI AC97 Channel Enable Register -- Set bits in SACCST */
37#define CCSR_SSI_SACCEN 0x54 77#define CCSR_SSI_SACCEN 0x54
78/* SSI AC97 Channel Disable Register -- Clear bits in SACCST */
38#define CCSR_SSI_SACCDIS 0x58 79#define CCSR_SSI_SACCDIS 0x58
39 80
81/* -- SSI Register Field Maps -- */
82
83/* SSI Control Register -- CCSR_SSI_SCR 0x10 */
40#define CCSR_SSI_SCR_SYNC_TX_FS 0x00001000 84#define CCSR_SSI_SCR_SYNC_TX_FS 0x00001000
41#define CCSR_SSI_SCR_RFR_CLK_DIS 0x00000800 85#define CCSR_SSI_SCR_RFR_CLK_DIS 0x00000800
42#define CCSR_SSI_SCR_TFR_CLK_DIS 0x00000400 86#define CCSR_SSI_SCR_TFR_CLK_DIS 0x00000400
@@ -52,6 +96,7 @@
52#define CCSR_SSI_SCR_TE 0x00000002 96#define CCSR_SSI_SCR_TE 0x00000002
53#define CCSR_SSI_SCR_SSIEN 0x00000001 97#define CCSR_SSI_SCR_SSIEN 0x00000001
54 98
99/* SSI Interrupt Status Register -- CCSR_SSI_SISR 0x14 */
55#define CCSR_SSI_SISR_RFRC 0x01000000 100#define CCSR_SSI_SISR_RFRC 0x01000000
56#define CCSR_SSI_SISR_TFRC 0x00800000 101#define CCSR_SSI_SISR_TFRC 0x00800000
57#define CCSR_SSI_SISR_CMDAU 0x00040000 102#define CCSR_SSI_SISR_CMDAU 0x00040000
@@ -74,6 +119,7 @@
74#define CCSR_SSI_SISR_TFE1 0x00000002 119#define CCSR_SSI_SISR_TFE1 0x00000002
75#define CCSR_SSI_SISR_TFE0 0x00000001 120#define CCSR_SSI_SISR_TFE0 0x00000001
76 121
122/* SSI Interrupt Enable Register -- CCSR_SSI_SIER 0x18 */
77#define CCSR_SSI_SIER_RFRC_EN 0x01000000 123#define CCSR_SSI_SIER_RFRC_EN 0x01000000
78#define CCSR_SSI_SIER_TFRC_EN 0x00800000 124#define CCSR_SSI_SIER_TFRC_EN 0x00800000
79#define CCSR_SSI_SIER_RDMAE 0x00400000 125#define CCSR_SSI_SIER_RDMAE 0x00400000
@@ -100,6 +146,7 @@
100#define CCSR_SSI_SIER_TFE1_EN 0x00000002 146#define CCSR_SSI_SIER_TFE1_EN 0x00000002
101#define CCSR_SSI_SIER_TFE0_EN 0x00000001 147#define CCSR_SSI_SIER_TFE0_EN 0x00000001
102 148
149/* SSI Transmit Configuration Register -- CCSR_SSI_STCR 0x1C */
103#define CCSR_SSI_STCR_TXBIT0 0x00000200 150#define CCSR_SSI_STCR_TXBIT0 0x00000200
104#define CCSR_SSI_STCR_TFEN1 0x00000100 151#define CCSR_SSI_STCR_TFEN1 0x00000100
105#define CCSR_SSI_STCR_TFEN0 0x00000080 152#define CCSR_SSI_STCR_TFEN0 0x00000080
@@ -111,6 +158,7 @@
111#define CCSR_SSI_STCR_TFSL 0x00000002 158#define CCSR_SSI_STCR_TFSL 0x00000002
112#define CCSR_SSI_STCR_TEFS 0x00000001 159#define CCSR_SSI_STCR_TEFS 0x00000001
113 160
161/* SSI Receive Configuration Register -- CCSR_SSI_SRCR 0x20 */
114#define CCSR_SSI_SRCR_RXEXT 0x00000400 162#define CCSR_SSI_SRCR_RXEXT 0x00000400
115#define CCSR_SSI_SRCR_RXBIT0 0x00000200 163#define CCSR_SSI_SRCR_RXBIT0 0x00000200
116#define CCSR_SSI_SRCR_RFEN1 0x00000100 164#define CCSR_SSI_SRCR_RFEN1 0x00000100
@@ -123,7 +171,10 @@
123#define CCSR_SSI_SRCR_RFSL 0x00000002 171#define CCSR_SSI_SRCR_RFSL 0x00000002
124#define CCSR_SSI_SRCR_REFS 0x00000001 172#define CCSR_SSI_SRCR_REFS 0x00000001
125 173
126/* STCCR and SRCCR */ 174/*
175 * SSI Transmit Clock Control Register -- CCSR_SSI_STCCR 0x24
176 * SSI Receive Clock Control Register -- CCSR_SSI_SRCCR 0x28
177 */
127#define CCSR_SSI_SxCCR_DIV2_SHIFT 18 178#define CCSR_SSI_SxCCR_DIV2_SHIFT 18
128#define CCSR_SSI_SxCCR_DIV2 0x00040000 179#define CCSR_SSI_SxCCR_DIV2 0x00040000
129#define CCSR_SSI_SxCCR_PSR_SHIFT 17 180#define CCSR_SSI_SxCCR_PSR_SHIFT 17
@@ -142,9 +193,10 @@
142 ((((x) - 1) << CCSR_SSI_SxCCR_PM_SHIFT) & CCSR_SSI_SxCCR_PM_MASK) 193 ((((x) - 1) << CCSR_SSI_SxCCR_PM_SHIFT) & CCSR_SSI_SxCCR_PM_MASK)
143 194
144/* 195/*
145 * The xFCNT bits are read-only, and the xFWM bits are read/write. Use the 196 * SSI FIFO Control/Status Register -- CCSR_SSI_SFCSR 0x2c
146 * CCSR_SSI_SFCSR_xFCNTy() macros to read the FIFO counters, and use the 197 *
147 * CCSR_SSI_SFCSR_xFWMy() macros to set the watermarks. 198 * Tx or Rx FIFO Counter -- CCSR_SSI_SFCSR_xFCNTy Read-Only
199 * Tx or Rx FIFO Watermarks -- CCSR_SSI_SFCSR_xFWMy Read/Write
148 */ 200 */
149#define CCSR_SSI_SFCSR_RFCNT1_SHIFT 28 201#define CCSR_SSI_SFCSR_RFCNT1_SHIFT 28
150#define CCSR_SSI_SFCSR_RFCNT1_MASK 0xF0000000 202#define CCSR_SSI_SFCSR_RFCNT1_MASK 0xF0000000
@@ -179,6 +231,7 @@
179#define CCSR_SSI_SFCSR_TFWM0(x) \ 231#define CCSR_SSI_SFCSR_TFWM0(x) \
180 (((x) << CCSR_SSI_SFCSR_TFWM0_SHIFT) & CCSR_SSI_SFCSR_TFWM0_MASK) 232 (((x) << CCSR_SSI_SFCSR_TFWM0_SHIFT) & CCSR_SSI_SFCSR_TFWM0_MASK)
181 233
234/* SSI Test Register -- CCSR_SSI_STR 0x30 */
182#define CCSR_SSI_STR_TEST 0x00008000 235#define CCSR_SSI_STR_TEST 0x00008000
183#define CCSR_SSI_STR_RCK2TCK 0x00004000 236#define CCSR_SSI_STR_RCK2TCK 0x00004000
184#define CCSR_SSI_STR_RFS2TFS 0x00002000 237#define CCSR_SSI_STR_RFS2TFS 0x00002000
@@ -188,6 +241,7 @@
188#define CCSR_SSI_STR_TFS2RFS 0x00000020 241#define CCSR_SSI_STR_TFS2RFS 0x00000020
189#define CCSR_SSI_STR_TXSTATE(x) ((x) & 0x1F) 242#define CCSR_SSI_STR_TXSTATE(x) ((x) & 0x1F)
190 243
244/* SSI Option Register -- CCSR_SSI_SOR 0x34 */
191#define CCSR_SSI_SOR_CLKOFF 0x00000040 245#define CCSR_SSI_SOR_CLKOFF 0x00000040
192#define CCSR_SSI_SOR_RX_CLR 0x00000020 246#define CCSR_SSI_SOR_RX_CLR 0x00000020
193#define CCSR_SSI_SOR_TX_CLR 0x00000010 247#define CCSR_SSI_SOR_TX_CLR 0x00000010
@@ -197,6 +251,7 @@
197#define CCSR_SSI_SOR_WAIT(x) (((x) & 3) << CCSR_SSI_SOR_WAIT_SHIFT) 251#define CCSR_SSI_SOR_WAIT(x) (((x) & 3) << CCSR_SSI_SOR_WAIT_SHIFT)
198#define CCSR_SSI_SOR_SYNRST 0x00000001 252#define CCSR_SSI_SOR_SYNRST 0x00000001
199 253
254/* SSI AC97 Control Register -- CCSR_SSI_SACNT 0x38 */
200#define CCSR_SSI_SACNT_FRDIV(x) (((x) & 0x3f) << 5) 255#define CCSR_SSI_SACNT_FRDIV(x) (((x) & 0x3f) << 5)
201#define CCSR_SSI_SACNT_WR 0x00000010 256#define CCSR_SSI_SACNT_WR 0x00000010
202#define CCSR_SSI_SACNT_RD 0x00000008 257#define CCSR_SSI_SACNT_RD 0x00000008
diff --git a/sound/soc/fsl/fsl_ssi_dbg.c b/sound/soc/fsl/fsl_ssi_dbg.c
index 5469ffbc0253..88d9e8e08905 100644
--- a/sound/soc/fsl/fsl_ssi_dbg.c
+++ b/sound/soc/fsl/fsl_ssi_dbg.c
@@ -82,9 +82,10 @@ void fsl_ssi_dbg_isr(struct fsl_ssi_dbg *dbg, u32 sisr)
82 dbg->stats.tfe0++; 82 dbg->stats.tfe0++;
83} 83}
84 84
85/* Show the statistics of a flag only if its interrupt is enabled. The 85/**
86 * compiler will optimze this code to a no-op if the interrupt is not 86 * Show the statistics of a flag only if its interrupt is enabled
87 * enabled. 87 *
88 * Compilers will optimize it to a no-op if the interrupt is disabled
88 */ 89 */
89#define SIER_SHOW(flag, name) \ 90#define SIER_SHOW(flag, name) \
90 do { \ 91 do { \
@@ -94,10 +95,9 @@ void fsl_ssi_dbg_isr(struct fsl_ssi_dbg *dbg, u32 sisr)
94 95
95 96
96/** 97/**
97 * fsl_sysfs_ssi_show: display SSI statistics 98 * Display the statistics for the current SSI device
98 * 99 *
99 * Display the statistics for the current SSI device. To avoid confusion, 100 * To avoid confusion, only show those counts that are enabled
100 * we only show those counts that are enabled.
101 */ 101 */
102static int fsl_ssi_stats_show(struct seq_file *s, void *unused) 102static int fsl_ssi_stats_show(struct seq_file *s, void *unused)
103{ 103{