linux/sound/pci/ctxfi/ctatc.c
<<
>>
Prefs
   1/**
   2 * Copyright (C) 2008, Creative Technology Ltd. All Rights Reserved.
   3 *
   4 * This source file is released under GPL v2 license (no other versions).
   5 * See the COPYING file included in the main directory of this source
   6 * distribution for the license terms and conditions.
   7 *
   8 * @File    ctatc.c
   9 *
  10 * @Brief
  11 * This file contains the implementation of the device resource management
  12 * object.
  13 *
  14 * @Author Liu Chun
  15 * @Date Mar 28 2008
  16 */
  17
  18#include "ctatc.h"
  19#include "ctpcm.h"
  20#include "ctmixer.h"
  21#include "cthardware.h"
  22#include "ctsrc.h"
  23#include "ctamixer.h"
  24#include "ctdaio.h"
  25#include "cttimer.h"
  26#include <linux/delay.h>
  27#include <linux/slab.h>
  28#include <sound/pcm.h>
  29#include <sound/control.h>
  30#include <sound/asoundef.h>
  31
  32#define MONO_SUM_SCALE  0x19a8  /* 2^(-0.5) in 14-bit floating format */
  33#define DAIONUM         7
  34#define MAX_MULTI_CHN   8
  35
  36#define IEC958_DEFAULT_CON ((IEC958_AES0_NONAUDIO \
  37                            | IEC958_AES0_CON_NOT_COPYRIGHT) \
  38                            | ((IEC958_AES1_CON_MIXER \
  39                            | IEC958_AES1_CON_ORIGINAL) << 8) \
  40                            | (0x10 << 16) \
  41                            | ((IEC958_AES3_CON_FS_48000) << 24))
  42
  43static struct snd_pci_quirk __devinitdata subsys_20k1_list[] = {
  44        SND_PCI_QUIRK(PCI_VENDOR_ID_CREATIVE, 0x0022, "SB055x", CTSB055X),
  45        SND_PCI_QUIRK(PCI_VENDOR_ID_CREATIVE, 0x002f, "SB055x", CTSB055X),
  46        SND_PCI_QUIRK(PCI_VENDOR_ID_CREATIVE, 0x0029, "SB073x", CTSB073X),
  47        SND_PCI_QUIRK(PCI_VENDOR_ID_CREATIVE, 0x0031, "SB073x", CTSB073X),
  48        SND_PCI_QUIRK_MASK(PCI_VENDOR_ID_CREATIVE, 0xf000, 0x6000,
  49                           "UAA", CTUAA),
  50        { } /* terminator */
  51};
  52
  53static struct snd_pci_quirk __devinitdata subsys_20k2_list[] = {
  54        SND_PCI_QUIRK(PCI_VENDOR_ID_CREATIVE, PCI_SUBDEVICE_ID_CREATIVE_SB0760,
  55                      "SB0760", CTSB0760),
  56        SND_PCI_QUIRK(PCI_VENDOR_ID_CREATIVE, PCI_SUBDEVICE_ID_CREATIVE_SB08801,
  57                      "SB0880", CTSB0880),
  58        SND_PCI_QUIRK(PCI_VENDOR_ID_CREATIVE, PCI_SUBDEVICE_ID_CREATIVE_SB08802,
  59                      "SB0880", CTSB0880),
  60        SND_PCI_QUIRK(PCI_VENDOR_ID_CREATIVE, PCI_SUBDEVICE_ID_CREATIVE_SB08803,
  61                      "SB0880", CTSB0880),
  62        SND_PCI_QUIRK_MASK(PCI_VENDOR_ID_CREATIVE, 0xf000,
  63                           PCI_SUBDEVICE_ID_CREATIVE_HENDRIX, "HENDRIX",
  64                           CTHENDRIX),
  65        { } /* terminator */
  66};
  67
  68static const char *ct_subsys_name[NUM_CTCARDS] = {
  69        /* 20k1 models */
  70        [CTSB055X]      = "SB055x",
  71        [CTSB073X]      = "SB073x",
  72        [CTUAA]         = "UAA",
  73        [CT20K1_UNKNOWN] = "Unknown",
  74        /* 20k2 models */
  75        [CTSB0760]      = "SB076x",
  76        [CTHENDRIX]     = "Hendrix",
  77        [CTSB0880]      = "SB0880",
  78        [CT20K2_UNKNOWN] = "Unknown",
  79};
  80
  81static struct {
  82        int (*create)(struct ct_atc *atc,
  83                        enum CTALSADEVS device, const char *device_name);
  84        int (*destroy)(void *alsa_dev);
  85        const char *public_name;
  86} alsa_dev_funcs[NUM_CTALSADEVS] = {
  87        [FRONT]         = { .create = ct_alsa_pcm_create,
  88                            .destroy = NULL,
  89                            .public_name = "Front/WaveIn"},
  90        [SURROUND]      = { .create = ct_alsa_pcm_create,
  91                            .destroy = NULL,
  92                            .public_name = "Surround"},
  93        [CLFE]          = { .create = ct_alsa_pcm_create,
  94                            .destroy = NULL,
  95                            .public_name = "Center/LFE"},
  96        [SIDE]          = { .create = ct_alsa_pcm_create,
  97                            .destroy = NULL,
  98                            .public_name = "Side"},
  99        [IEC958]        = { .create = ct_alsa_pcm_create,
 100                            .destroy = NULL,
 101                            .public_name = "IEC958 Non-audio"},
 102
 103        [MIXER]         = { .create = ct_alsa_mix_create,
 104                            .destroy = NULL,
 105                            .public_name = "Mixer"}
 106};
 107
 108typedef int (*create_t)(void *, void **);
 109typedef int (*destroy_t)(void *);
 110
 111static struct {
 112        int (*create)(void *hw, void **rmgr);
 113        int (*destroy)(void *mgr);
 114} rsc_mgr_funcs[NUM_RSCTYP] = {
 115        [SRC]           = { .create     = (create_t)src_mgr_create,
 116                            .destroy    = (destroy_t)src_mgr_destroy    },
 117        [SRCIMP]        = { .create     = (create_t)srcimp_mgr_create,
 118                            .destroy    = (destroy_t)srcimp_mgr_destroy },
 119        [AMIXER]        = { .create     = (create_t)amixer_mgr_create,
 120                            .destroy    = (destroy_t)amixer_mgr_destroy },
 121        [SUM]           = { .create     = (create_t)sum_mgr_create,
 122                            .destroy    = (destroy_t)sum_mgr_destroy    },
 123        [DAIO]          = { .create     = (create_t)daio_mgr_create,
 124                            .destroy    = (destroy_t)daio_mgr_destroy   }
 125};
 126
 127static int
 128atc_pcm_release_resources(struct ct_atc *atc, struct ct_atc_pcm *apcm);
 129
 130/* *
 131 * Only mono and interleaved modes are supported now.
 132 * Always allocates a contiguous channel block.
 133 * */
 134
 135static int ct_map_audio_buffer(struct ct_atc *atc, struct ct_atc_pcm *apcm)
 136{
 137        struct snd_pcm_runtime *runtime;
 138        struct ct_vm *vm;
 139
 140        if (!apcm->substream)
 141                return 0;
 142
 143        runtime = apcm->substream->runtime;
 144        vm = atc->vm;
 145
 146        apcm->vm_block = vm->map(vm, apcm->substream, runtime->dma_bytes);
 147
 148        if (!apcm->vm_block)
 149                return -ENOENT;
 150
 151        return 0;
 152}
 153
 154static void ct_unmap_audio_buffer(struct ct_atc *atc, struct ct_atc_pcm *apcm)
 155{
 156        struct ct_vm *vm;
 157
 158        if (!apcm->vm_block)
 159                return;
 160
 161        vm = atc->vm;
 162
 163        vm->unmap(vm, apcm->vm_block);
 164
 165        apcm->vm_block = NULL;
 166}
 167
 168static unsigned long atc_get_ptp_phys(struct ct_atc *atc, int index)
 169{
 170        return atc->vm->get_ptp_phys(atc->vm, index);
 171}
 172
 173static unsigned int convert_format(snd_pcm_format_t snd_format)
 174{
 175        switch (snd_format) {
 176        case SNDRV_PCM_FORMAT_U8:
 177                return SRC_SF_U8;
 178        case SNDRV_PCM_FORMAT_S16_LE:
 179                return SRC_SF_S16;
 180        case SNDRV_PCM_FORMAT_S24_3LE:
 181                return SRC_SF_S24;
 182        case SNDRV_PCM_FORMAT_S32_LE:
 183                return SRC_SF_S32;
 184        case SNDRV_PCM_FORMAT_FLOAT_LE:
 185                return SRC_SF_F32;
 186        default:
 187                printk(KERN_ERR "ctxfi: not recognized snd format is %d \n",
 188                        snd_format);
 189                return SRC_SF_S16;
 190        }
 191}
 192
 193static unsigned int
 194atc_get_pitch(unsigned int input_rate, unsigned int output_rate)
 195{
 196        unsigned int pitch;
 197        int b;
 198
 199        /* get pitch and convert to fixed-point 8.24 format. */
 200        pitch = (input_rate / output_rate) << 24;
 201        input_rate %= output_rate;
 202        input_rate /= 100;
 203        output_rate /= 100;
 204        for (b = 31; ((b >= 0) && !(input_rate >> b)); )
 205                b--;
 206
 207        if (b >= 0) {
 208                input_rate <<= (31 - b);
 209                input_rate /= output_rate;
 210                b = 24 - (31 - b);
 211                if (b >= 0)
 212                        input_rate <<= b;
 213                else
 214                        input_rate >>= -b;
 215
 216                pitch |= input_rate;
 217        }
 218
 219        return pitch;
 220}
 221
 222static int select_rom(unsigned int pitch)
 223{
 224        if (pitch > 0x00428f5c && pitch < 0x01b851ec) {
 225                /* 0.26 <= pitch <= 1.72 */
 226                return 1;
 227        } else if (pitch == 0x01d66666 || pitch == 0x01d66667) {
 228                /* pitch == 1.8375 */
 229                return 2;
 230        } else if (pitch == 0x02000000) {
 231                /* pitch == 2 */
 232                return 3;
 233        } else if (pitch <= 0x08000000) {
 234                /* 0 <= pitch <= 8 */
 235                return 0;
 236        } else {
 237                return -ENOENT;
 238        }
 239}
 240
 241static int atc_pcm_playback_prepare(struct ct_atc *atc, struct ct_atc_pcm *apcm)
 242{
 243        struct src_mgr *src_mgr = atc->rsc_mgrs[SRC];
 244        struct amixer_mgr *amixer_mgr = atc->rsc_mgrs[AMIXER];
 245        struct src_desc desc = {0};
 246        struct amixer_desc mix_dsc = {0};
 247        struct src *src;
 248        struct amixer *amixer;
 249        int err;
 250        int n_amixer = apcm->substream->runtime->channels, i = 0;
 251        int device = apcm->substream->pcm->device;
 252        unsigned int pitch;
 253
 254        /* first release old resources */
 255        atc_pcm_release_resources(atc, apcm);
 256
 257        /* Get SRC resource */
 258        desc.multi = apcm->substream->runtime->channels;
 259        desc.msr = atc->msr;
 260        desc.mode = MEMRD;
 261        err = src_mgr->get_src(src_mgr, &desc, (struct src **)&apcm->src);
 262        if (err)
 263                goto error1;
 264
 265        pitch = atc_get_pitch(apcm->substream->runtime->rate,
 266                                                (atc->rsr * atc->msr));
 267        src = apcm->src;
 268        src->ops->set_pitch(src, pitch);
 269        src->ops->set_rom(src, select_rom(pitch));
 270        src->ops->set_sf(src, convert_format(apcm->substream->runtime->format));
 271        src->ops->set_pm(src, (src->ops->next_interleave(src) != NULL));
 272
 273        /* Get AMIXER resource */
 274        n_amixer = (n_amixer < 2) ? 2 : n_amixer;
 275        apcm->amixers = kzalloc(sizeof(void *)*n_amixer, GFP_KERNEL);
 276        if (!apcm->amixers) {
 277                err = -ENOMEM;
 278                goto error1;
 279        }
 280        mix_dsc.msr = atc->msr;
 281        for (i = 0, apcm->n_amixer = 0; i < n_amixer; i++) {
 282                err = amixer_mgr->get_amixer(amixer_mgr, &mix_dsc,
 283                                        (struct amixer **)&apcm->amixers[i]);
 284                if (err)
 285                        goto error1;
 286
 287                apcm->n_amixer++;
 288        }
 289
 290        /* Set up device virtual mem map */
 291        err = ct_map_audio_buffer(atc, apcm);
 292        if (err < 0)
 293                goto error1;
 294
 295        /* Connect resources */
 296        src = apcm->src;
 297        for (i = 0; i < n_amixer; i++) {
 298                amixer = apcm->amixers[i];
 299                mutex_lock(&atc->atc_mutex);
 300                amixer->ops->setup(amixer, &src->rsc,
 301                                        INIT_VOL, atc->pcm[i+device*2]);
 302                mutex_unlock(&atc->atc_mutex);
 303                src = src->ops->next_interleave(src);
 304                if (!src)
 305                        src = apcm->src;
 306        }
 307
 308        ct_timer_prepare(apcm->timer);
 309
 310        return 0;
 311
 312error1:
 313        atc_pcm_release_resources(atc, apcm);
 314        return err;
 315}
 316
 317static int
 318atc_pcm_release_resources(struct ct_atc *atc, struct ct_atc_pcm *apcm)
 319{
 320        struct src_mgr *src_mgr = atc->rsc_mgrs[SRC];
 321        struct srcimp_mgr *srcimp_mgr = atc->rsc_mgrs[SRCIMP];
 322        struct amixer_mgr *amixer_mgr = atc->rsc_mgrs[AMIXER];
 323        struct sum_mgr *sum_mgr = atc->rsc_mgrs[SUM];
 324        struct srcimp *srcimp;
 325        int i;
 326
 327        if (apcm->srcimps) {
 328                for (i = 0; i < apcm->n_srcimp; i++) {
 329                        srcimp = apcm->srcimps[i];
 330                        srcimp->ops->unmap(srcimp);
 331                        srcimp_mgr->put_srcimp(srcimp_mgr, srcimp);
 332                        apcm->srcimps[i] = NULL;
 333                }
 334                kfree(apcm->srcimps);
 335                apcm->srcimps = NULL;
 336        }
 337
 338        if (apcm->srccs) {
 339                for (i = 0; i < apcm->n_srcc; i++) {
 340                        src_mgr->put_src(src_mgr, apcm->srccs[i]);
 341                        apcm->srccs[i] = NULL;
 342                }
 343                kfree(apcm->srccs);
 344                apcm->srccs = NULL;
 345        }
 346
 347        if (apcm->amixers) {
 348                for (i = 0; i < apcm->n_amixer; i++) {
 349                        amixer_mgr->put_amixer(amixer_mgr, apcm->amixers[i]);
 350                        apcm->amixers[i] = NULL;
 351                }
 352                kfree(apcm->amixers);
 353                apcm->amixers = NULL;
 354        }
 355
 356        if (apcm->mono) {
 357                sum_mgr->put_sum(sum_mgr, apcm->mono);
 358                apcm->mono = NULL;
 359        }
 360
 361        if (apcm->src) {
 362                src_mgr->put_src(src_mgr, apcm->src);
 363                apcm->src = NULL;
 364        }
 365
 366        if (apcm->vm_block) {
 367                /* Undo device virtual mem map */
 368                ct_unmap_audio_buffer(atc, apcm);
 369                apcm->vm_block = NULL;
 370        }
 371
 372        return 0;
 373}
 374
 375static int atc_pcm_playback_start(struct ct_atc *atc, struct ct_atc_pcm *apcm)
 376{
 377        unsigned int max_cisz;
 378        struct src *src = apcm->src;
 379
 380        if (apcm->started)
 381                return 0;
 382        apcm->started = 1;
 383
 384        max_cisz = src->multi * src->rsc.msr;
 385        max_cisz = 0x80 * (max_cisz < 8 ? max_cisz : 8);
 386
 387        src->ops->set_sa(src, apcm->vm_block->addr);
 388        src->ops->set_la(src, apcm->vm_block->addr + apcm->vm_block->size);
 389        src->ops->set_ca(src, apcm->vm_block->addr + max_cisz);
 390        src->ops->set_cisz(src, max_cisz);
 391
 392        src->ops->set_bm(src, 1);
 393        src->ops->set_state(src, SRC_STATE_INIT);
 394        src->ops->commit_write(src);
 395
 396        ct_timer_start(apcm->timer);
 397        return 0;
 398}
 399
 400static int atc_pcm_stop(struct ct_atc *atc, struct ct_atc_pcm *apcm)
 401{
 402        struct src *src;
 403        int i;
 404
 405        ct_timer_stop(apcm->timer);
 406
 407        src = apcm->src;
 408        src->ops->set_bm(src, 0);
 409        src->ops->set_state(src, SRC_STATE_OFF);
 410        src->ops->commit_write(src);
 411
 412        if (apcm->srccs) {
 413                for (i = 0; i < apcm->n_srcc; i++) {
 414                        src = apcm->srccs[i];
 415                        src->ops->set_bm(src, 0);
 416                        src->ops->set_state(src, SRC_STATE_OFF);
 417                        src->ops->commit_write(src);
 418                }
 419        }
 420
 421        apcm->started = 0;
 422
 423        return 0;
 424}
 425
 426static int
 427atc_pcm_playback_position(struct ct_atc *atc, struct ct_atc_pcm *apcm)
 428{
 429        struct src *src = apcm->src;
 430        u32 size, max_cisz;
 431        int position;
 432
 433        if (!src)
 434                return 0;
 435        position = src->ops->get_ca(src);
 436
 437        size = apcm->vm_block->size;
 438        max_cisz = src->multi * src->rsc.msr;
 439        max_cisz = 128 * (max_cisz < 8 ? max_cisz : 8);
 440
 441        return (position + size - max_cisz - apcm->vm_block->addr) % size;
 442}
 443
 444struct src_node_conf_t {
 445        unsigned int pitch;
 446        unsigned int msr:8;
 447        unsigned int mix_msr:8;
 448        unsigned int imp_msr:8;
 449        unsigned int vo:1;
 450};
 451
 452static void setup_src_node_conf(struct ct_atc *atc, struct ct_atc_pcm *apcm,
 453                                struct src_node_conf_t *conf, int *n_srcc)
 454{
 455        unsigned int pitch;
 456
 457        /* get pitch and convert to fixed-point 8.24 format. */
 458        pitch = atc_get_pitch((atc->rsr * atc->msr),
 459                                apcm->substream->runtime->rate);
 460        *n_srcc = 0;
 461
 462        if (1 == atc->msr) {
 463                *n_srcc = apcm->substream->runtime->channels;
 464                conf[0].pitch = pitch;
 465                conf[0].mix_msr = conf[0].imp_msr = conf[0].msr = 1;
 466                conf[0].vo = 1;
 467        } else if (2 == atc->msr) {
 468                if (0x8000000 < pitch) {
 469                        /* Need two-stage SRCs, SRCIMPs and
 470                         * AMIXERs for converting format */
 471                        conf[0].pitch = (atc->msr << 24);
 472                        conf[0].msr = conf[0].mix_msr = 1;
 473                        conf[0].imp_msr = atc->msr;
 474                        conf[0].vo = 0;
 475                        conf[1].pitch = atc_get_pitch(atc->rsr,
 476                                        apcm->substream->runtime->rate);
 477                        conf[1].msr = conf[1].mix_msr = conf[1].imp_msr = 1;
 478                        conf[1].vo = 1;
 479                        *n_srcc = apcm->substream->runtime->channels * 2;
 480                } else if (0x1000000 < pitch) {
 481                        /* Need one-stage SRCs, SRCIMPs and
 482                         * AMIXERs for converting format */
 483                        conf[0].pitch = pitch;
 484                        conf[0].msr = conf[0].mix_msr
 485                                    = conf[0].imp_msr = atc->msr;
 486                        conf[0].vo = 1;
 487                        *n_srcc = apcm->substream->runtime->channels;
 488                }
 489        }
 490}
 491
 492static int
 493atc_pcm_capture_get_resources(struct ct_atc *atc, struct ct_atc_pcm *apcm)
 494{
 495        struct src_mgr *src_mgr = atc->rsc_mgrs[SRC];
 496        struct srcimp_mgr *srcimp_mgr = atc->rsc_mgrs[SRCIMP];
 497        struct amixer_mgr *amixer_mgr = atc->rsc_mgrs[AMIXER];
 498        struct sum_mgr *sum_mgr = atc->rsc_mgrs[SUM];
 499        struct src_desc src_dsc = {0};
 500        struct src *src;
 501        struct srcimp_desc srcimp_dsc = {0};
 502        struct srcimp *srcimp;
 503        struct amixer_desc mix_dsc = {0};
 504        struct sum_desc sum_dsc = {0};
 505        unsigned int pitch;
 506        int multi, err, i;
 507        int n_srcimp, n_amixer, n_srcc, n_sum;
 508        struct src_node_conf_t src_node_conf[2] = {{0} };
 509
 510        /* first release old resources */
 511        atc_pcm_release_resources(atc, apcm);
 512
 513        /* The numbers of converting SRCs and SRCIMPs should be determined
 514         * by pitch value. */
 515
 516        multi = apcm->substream->runtime->channels;
 517
 518        /* get pitch and convert to fixed-point 8.24 format. */
 519        pitch = atc_get_pitch((atc->rsr * atc->msr),
 520                                apcm->substream->runtime->rate);
 521
 522        setup_src_node_conf(atc, apcm, src_node_conf, &n_srcc);
 523        n_sum = (1 == multi) ? 1 : 0;
 524        n_amixer = n_sum * 2 + n_srcc;
 525        n_srcimp = n_srcc;
 526        if ((multi > 1) && (0x8000000 >= pitch)) {
 527                /* Need extra AMIXERs and SRCIMPs for special treatment
 528                 * of interleaved recording of conjugate channels */
 529                n_amixer += multi * atc->msr;
 530                n_srcimp += multi * atc->msr;
 531        } else {
 532                n_srcimp += multi;
 533        }
 534
 535        if (n_srcc) {
 536                apcm->srccs = kzalloc(sizeof(void *)*n_srcc, GFP_KERNEL);
 537                if (!apcm->srccs)
 538                        return -ENOMEM;
 539        }
 540        if (n_amixer) {
 541                apcm->amixers = kzalloc(sizeof(void *)*n_amixer, GFP_KERNEL);
 542                if (!apcm->amixers) {
 543                        err = -ENOMEM;
 544                        goto error1;
 545                }
 546        }
 547        apcm->srcimps = kzalloc(sizeof(void *)*n_srcimp, GFP_KERNEL);
 548        if (!apcm->srcimps) {
 549                err = -ENOMEM;
 550                goto error1;
 551        }
 552
 553        /* Allocate SRCs for sample rate conversion if needed */
 554        src_dsc.multi = 1;
 555        src_dsc.mode = ARCRW;
 556        for (i = 0, apcm->n_srcc = 0; i < n_srcc; i++) {
 557                src_dsc.msr = src_node_conf[i/multi].msr;
 558                err = src_mgr->get_src(src_mgr, &src_dsc,
 559                                        (struct src **)&apcm->srccs[i]);
 560                if (err)
 561                        goto error1;
 562
 563                src = apcm->srccs[i];
 564                pitch = src_node_conf[i/multi].pitch;
 565                src->ops->set_pitch(src, pitch);
 566                src->ops->set_rom(src, select_rom(pitch));
 567                src->ops->set_vo(src, src_node_conf[i/multi].vo);
 568
 569                apcm->n_srcc++;
 570        }
 571
 572        /* Allocate AMIXERs for routing SRCs of conversion if needed */
 573        for (i = 0, apcm->n_amixer = 0; i < n_amixer; i++) {
 574                if (i < (n_sum*2))
 575                        mix_dsc.msr = atc->msr;
 576                else if (i < (n_sum*2+n_srcc))
 577                        mix_dsc.msr = src_node_conf[(i-n_sum*2)/multi].mix_msr;
 578                else
 579                        mix_dsc.msr = 1;
 580
 581                err = amixer_mgr->get_amixer(amixer_mgr, &mix_dsc,
 582                                        (struct amixer **)&apcm->amixers[i]);
 583                if (err)
 584                        goto error1;
 585
 586                apcm->n_amixer++;
 587        }
 588
 589        /* Allocate a SUM resource to mix all input channels together */
 590        sum_dsc.msr = atc->msr;
 591        err = sum_mgr->get_sum(sum_mgr, &sum_dsc, (struct sum **)&apcm->mono);
 592        if (err)
 593                goto error1;
 594
 595        pitch = atc_get_pitch((atc->rsr * atc->msr),
 596                                apcm->substream->runtime->rate);
 597        /* Allocate SRCIMP resources */
 598        for (i = 0, apcm->n_srcimp = 0; i < n_srcimp; i++) {
 599                if (i < (n_srcc))
 600                        srcimp_dsc.msr = src_node_conf[i/multi].imp_msr;
 601                else if (1 == multi)
 602                        srcimp_dsc.msr = (pitch <= 0x8000000) ? atc->msr : 1;
 603                else
 604                        srcimp_dsc.msr = 1;
 605
 606                err = srcimp_mgr->get_srcimp(srcimp_mgr, &srcimp_dsc, &srcimp);
 607                if (err)
 608                        goto error1;
 609
 610                apcm->srcimps[i] = srcimp;
 611                apcm->n_srcimp++;
 612        }
 613
 614        /* Allocate a SRC for writing data to host memory */
 615        src_dsc.multi = apcm->substream->runtime->channels;
 616        src_dsc.msr = 1;
 617        src_dsc.mode = MEMWR;
 618        err = src_mgr->get_src(src_mgr, &src_dsc, (struct src **)&apcm->src);
 619        if (err)
 620                goto error1;
 621
 622        src = apcm->src;
 623        src->ops->set_pitch(src, pitch);
 624
 625        /* Set up device virtual mem map */
 626        err = ct_map_audio_buffer(atc, apcm);
 627        if (err < 0)
 628                goto error1;
 629
 630        return 0;
 631
 632error1:
 633        atc_pcm_release_resources(atc, apcm);
 634        return err;
 635}
 636
 637static int atc_pcm_capture_prepare(struct ct_atc *atc, struct ct_atc_pcm *apcm)
 638{
 639        struct src *src;
 640        struct amixer *amixer;
 641        struct srcimp *srcimp;
 642        struct ct_mixer *mixer = atc->mixer;
 643        struct sum *mono;
 644        struct rsc *out_ports[8] = {NULL};
 645        int err, i, j, n_sum, multi;
 646        unsigned int pitch;
 647        int mix_base = 0, imp_base = 0;
 648
 649        atc_pcm_release_resources(atc, apcm);
 650
 651        /* Get needed resources. */
 652        err = atc_pcm_capture_get_resources(atc, apcm);
 653        if (err)
 654                return err;
 655
 656        /* Connect resources */
 657        mixer->get_output_ports(mixer, MIX_PCMO_FRONT,
 658                                &out_ports[0], &out_ports[1]);
 659
 660        multi = apcm->substream->runtime->channels;
 661        if (1 == multi) {
 662                mono = apcm->mono;
 663                for (i = 0; i < 2; i++) {
 664                        amixer = apcm->amixers[i];
 665                        amixer->ops->setup(amixer, out_ports[i],
 666                                                MONO_SUM_SCALE, mono);
 667                }
 668                out_ports[0] = &mono->rsc;
 669                n_sum = 1;
 670                mix_base = n_sum * 2;
 671        }
 672
 673        for (i = 0; i < apcm->n_srcc; i++) {
 674                src = apcm->srccs[i];
 675                srcimp = apcm->srcimps[imp_base+i];
 676                amixer = apcm->amixers[mix_base+i];
 677                srcimp->ops->map(srcimp, src, out_ports[i%multi]);
 678                amixer->ops->setup(amixer, &src->rsc, INIT_VOL, NULL);
 679                out_ports[i%multi] = &amixer->rsc;
 680        }
 681
 682        pitch = atc_get_pitch((atc->rsr * atc->msr),
 683                                apcm->substream->runtime->rate);
 684
 685        if ((multi > 1) && (pitch <= 0x8000000)) {
 686                /* Special connection for interleaved
 687                 * recording with conjugate channels */
 688                for (i = 0; i < multi; i++) {
 689                        out_ports[i]->ops->master(out_ports[i]);
 690                        for (j = 0; j < atc->msr; j++) {
 691                                amixer = apcm->amixers[apcm->n_srcc+j*multi+i];
 692                                amixer->ops->set_input(amixer, out_ports[i]);
 693                                amixer->ops->set_scale(amixer, INIT_VOL);
 694                                amixer->ops->set_sum(amixer, NULL);
 695                                amixer->ops->commit_raw_write(amixer);
 696                                out_ports[i]->ops->next_conj(out_ports[i]);
 697
 698                                srcimp = apcm->srcimps[apcm->n_srcc+j*multi+i];
 699                                srcimp->ops->map(srcimp, apcm->src,
 700                                                        &amixer->rsc);
 701                        }
 702                }
 703        } else {
 704                for (i = 0; i < multi; i++) {
 705                        srcimp = apcm->srcimps[apcm->n_srcc+i];
 706                        srcimp->ops->map(srcimp, apcm->src, out_ports[i]);
 707                }
 708        }
 709
 710        ct_timer_prepare(apcm->timer);
 711
 712        return 0;
 713}
 714
 715static int atc_pcm_capture_start(struct ct_atc *atc, struct ct_atc_pcm *apcm)
 716{
 717        struct src *src;
 718        struct src_mgr *src_mgr = atc->rsc_mgrs[SRC];
 719        int i, multi;
 720
 721        if (apcm->started)
 722                return 0;
 723
 724        apcm->started = 1;
 725        multi = apcm->substream->runtime->channels;
 726        /* Set up converting SRCs */
 727        for (i = 0; i < apcm->n_srcc; i++) {
 728                src = apcm->srccs[i];
 729                src->ops->set_pm(src, ((i%multi) != (multi-1)));
 730                src_mgr->src_disable(src_mgr, src);
 731        }
 732
 733        /*  Set up recording SRC */
 734        src = apcm->src;
 735        src->ops->set_sf(src, convert_format(apcm->substream->runtime->format));
 736        src->ops->set_sa(src, apcm->vm_block->addr);
 737        src->ops->set_la(src, apcm->vm_block->addr + apcm->vm_block->size);
 738        src->ops->set_ca(src, apcm->vm_block->addr);
 739        src_mgr->src_disable(src_mgr, src);
 740
 741        /* Disable relevant SRCs firstly */
 742        src_mgr->commit_write(src_mgr);
 743
 744        /* Enable SRCs respectively */
 745        for (i = 0; i < apcm->n_srcc; i++) {
 746                src = apcm->srccs[i];
 747                src->ops->set_state(src, SRC_STATE_RUN);
 748                src->ops->commit_write(src);
 749                src_mgr->src_enable_s(src_mgr, src);
 750        }
 751        src = apcm->src;
 752        src->ops->set_bm(src, 1);
 753        src->ops->set_state(src, SRC_STATE_RUN);
 754        src->ops->commit_write(src);
 755        src_mgr->src_enable_s(src_mgr, src);
 756
 757        /* Enable relevant SRCs synchronously */
 758        src_mgr->commit_write(src_mgr);
 759
 760        ct_timer_start(apcm->timer);
 761        return 0;
 762}
 763
 764static int
 765atc_pcm_capture_position(struct ct_atc *atc, struct ct_atc_pcm *apcm)
 766{
 767        struct src *src = apcm->src;
 768
 769        if (!src)
 770                return 0;
 771        return src->ops->get_ca(src) - apcm->vm_block->addr;
 772}
 773
 774static int spdif_passthru_playback_get_resources(struct ct_atc *atc,
 775                                                 struct ct_atc_pcm *apcm)
 776{
 777        struct src_mgr *src_mgr = atc->rsc_mgrs[SRC];
 778        struct amixer_mgr *amixer_mgr = atc->rsc_mgrs[AMIXER];
 779        struct src_desc desc = {0};
 780        struct amixer_desc mix_dsc = {0};
 781        struct src *src;
 782        int err;
 783        int n_amixer = apcm->substream->runtime->channels, i;
 784        unsigned int pitch, rsr = atc->pll_rate;
 785
 786        /* first release old resources */
 787        atc_pcm_release_resources(atc, apcm);
 788
 789        /* Get SRC resource */
 790        desc.multi = apcm->substream->runtime->channels;
 791        desc.msr = 1;
 792        while (apcm->substream->runtime->rate > (rsr * desc.msr))
 793                desc.msr <<= 1;
 794
 795        desc.mode = MEMRD;
 796        err = src_mgr->get_src(src_mgr, &desc, (struct src **)&apcm->src);
 797        if (err)
 798                goto error1;
 799
 800        pitch = atc_get_pitch(apcm->substream->runtime->rate, (rsr * desc.msr));
 801        src = apcm->src;
 802        src->ops->set_pitch(src, pitch);
 803        src->ops->set_rom(src, select_rom(pitch));
 804        src->ops->set_sf(src, convert_format(apcm->substream->runtime->format));
 805        src->ops->set_pm(src, (src->ops->next_interleave(src) != NULL));
 806        src->ops->set_bp(src, 1);
 807
 808        /* Get AMIXER resource */
 809        n_amixer = (n_amixer < 2) ? 2 : n_amixer;
 810        apcm->amixers = kzalloc(sizeof(void *)*n_amixer, GFP_KERNEL);
 811        if (!apcm->amixers) {
 812                err = -ENOMEM;
 813                goto error1;
 814        }
 815        mix_dsc.msr = desc.msr;
 816        for (i = 0, apcm->n_amixer = 0; i < n_amixer; i++) {
 817                err = amixer_mgr->get_amixer(amixer_mgr, &mix_dsc,
 818                                        (struct amixer **)&apcm->amixers[i]);
 819                if (err)
 820                        goto error1;
 821
 822                apcm->n_amixer++;
 823        }
 824
 825        /* Set up device virtual mem map */
 826        err = ct_map_audio_buffer(atc, apcm);
 827        if (err < 0)
 828                goto error1;
 829
 830        return 0;
 831
 832error1:
 833        atc_pcm_release_resources(atc, apcm);
 834        return err;
 835}
 836
 837static int atc_pll_init(struct ct_atc *atc, int rate)
 838{
 839        struct hw *hw = atc->hw;
 840        int err;
 841        err = hw->pll_init(hw, rate);
 842        atc->pll_rate = err ? 0 : rate;
 843        return err;
 844}
 845
 846static int
 847spdif_passthru_playback_setup(struct ct_atc *atc, struct ct_atc_pcm *apcm)
 848{
 849        struct dao *dao = container_of(atc->daios[SPDIFOO], struct dao, daio);
 850        unsigned int rate = apcm->substream->runtime->rate;
 851        unsigned int status;
 852        int err = 0;
 853        unsigned char iec958_con_fs;
 854
 855        switch (rate) {
 856        case 48000:
 857                iec958_con_fs = IEC958_AES3_CON_FS_48000;
 858                break;
 859        case 44100:
 860                iec958_con_fs = IEC958_AES3_CON_FS_44100;
 861                break;
 862        case 32000:
 863                iec958_con_fs = IEC958_AES3_CON_FS_32000;
 864                break;
 865        default:
 866                return -ENOENT;
 867        }
 868
 869        mutex_lock(&atc->atc_mutex);
 870        dao->ops->get_spos(dao, &status);
 871        if (((status >> 24) & IEC958_AES3_CON_FS) != iec958_con_fs) {
 872                status &= ((~IEC958_AES3_CON_FS) << 24);
 873                status |= (iec958_con_fs << 24);
 874                dao->ops->set_spos(dao, status);
 875                dao->ops->commit_write(dao);
 876        }
 877        if ((rate != atc->pll_rate) && (32000 != rate))
 878                err = atc_pll_init(atc, rate);
 879        mutex_unlock(&atc->atc_mutex);
 880
 881        return err;
 882}
 883
 884static int
 885spdif_passthru_playback_prepare(struct ct_atc *atc, struct ct_atc_pcm *apcm)
 886{
 887        struct src *src;
 888        struct amixer *amixer;
 889        struct dao *dao;
 890        int err;
 891        int i;
 892
 893        atc_pcm_release_resources(atc, apcm);
 894
 895        /* Configure SPDIFOO and PLL to passthrough mode;
 896         * determine pll_rate. */
 897        err = spdif_passthru_playback_setup(atc, apcm);
 898        if (err)
 899                return err;
 900
 901        /* Get needed resources. */
 902        err = spdif_passthru_playback_get_resources(atc, apcm);
 903        if (err)
 904                return err;
 905
 906        /* Connect resources */
 907        src = apcm->src;
 908        for (i = 0; i < apcm->n_amixer; i++) {
 909                amixer = apcm->amixers[i];
 910                amixer->ops->setup(amixer, &src->rsc, INIT_VOL, NULL);
 911                src = src->ops->next_interleave(src);
 912                if (!src)
 913                        src = apcm->src;
 914        }
 915        /* Connect to SPDIFOO */
 916        mutex_lock(&atc->atc_mutex);
 917        dao = container_of(atc->daios[SPDIFOO], struct dao, daio);
 918        amixer = apcm->amixers[0];
 919        dao->ops->set_left_input(dao, &amixer->rsc);
 920        amixer = apcm->amixers[1];
 921        dao->ops->set_right_input(dao, &amixer->rsc);
 922        mutex_unlock(&atc->atc_mutex);
 923
 924        ct_timer_prepare(apcm->timer);
 925
 926        return 0;
 927}
 928
 929static int atc_select_line_in(struct ct_atc *atc)
 930{
 931        struct hw *hw = atc->hw;
 932        struct ct_mixer *mixer = atc->mixer;
 933        struct src *src;
 934
 935        if (hw->is_adc_source_selected(hw, ADC_LINEIN))
 936                return 0;
 937
 938        mixer->set_input_left(mixer, MIX_MIC_IN, NULL);
 939        mixer->set_input_right(mixer, MIX_MIC_IN, NULL);
 940
 941        hw->select_adc_source(hw, ADC_LINEIN);
 942
 943        src = atc->srcs[2];
 944        mixer->set_input_left(mixer, MIX_LINE_IN, &src->rsc);
 945        src = atc->srcs[3];
 946        mixer->set_input_right(mixer, MIX_LINE_IN, &src->rsc);
 947
 948        return 0;
 949}
 950
 951static int atc_select_mic_in(struct ct_atc *atc)
 952{
 953        struct hw *hw = atc->hw;
 954        struct ct_mixer *mixer = atc->mixer;
 955        struct src *src;
 956
 957        if (hw->is_adc_source_selected(hw, ADC_MICIN))
 958                return 0;
 959
 960        mixer->set_input_left(mixer, MIX_LINE_IN, NULL);
 961        mixer->set_input_right(mixer, MIX_LINE_IN, NULL);
 962
 963        hw->select_adc_source(hw, ADC_MICIN);
 964
 965        src = atc->srcs[2];
 966        mixer->set_input_left(mixer, MIX_MIC_IN, &src->rsc);
 967        src = atc->srcs[3];
 968        mixer->set_input_right(mixer, MIX_MIC_IN, &src->rsc);
 969
 970        return 0;
 971}
 972
 973static int atc_have_digit_io_switch(struct ct_atc *atc)
 974{
 975        struct hw *hw = atc->hw;
 976
 977        return hw->have_digit_io_switch(hw);
 978}
 979
 980static int atc_select_digit_io(struct ct_atc *atc)
 981{
 982        struct hw *hw = atc->hw;
 983
 984        if (hw->is_adc_source_selected(hw, ADC_NONE))
 985                return 0;
 986
 987        hw->select_adc_source(hw, ADC_NONE);
 988
 989        return 0;
 990}
 991
 992static int atc_daio_unmute(struct ct_atc *atc, unsigned char state, int type)
 993{
 994        struct daio_mgr *daio_mgr = atc->rsc_mgrs[DAIO];
 995
 996        if (state)
 997                daio_mgr->daio_enable(daio_mgr, atc->daios[type]);
 998        else
 999                daio_mgr->daio_disable(daio_mgr, atc->daios[type]);
1000
1001        daio_mgr->commit_write(daio_mgr);
1002
1003        return 0;
1004}
1005
1006static int
1007atc_dao_get_status(struct ct_atc *atc, unsigned int *status, int type)
1008{
1009        struct dao *dao = container_of(atc->daios[type], struct dao, daio);
1010        return dao->ops->get_spos(dao, status);
1011}
1012
1013static int
1014atc_dao_set_status(struct ct_atc *atc, unsigned int status, int type)
1015{
1016        struct dao *dao = container_of(atc->daios[type], struct dao, daio);
1017
1018        dao->ops->set_spos(dao, status);
1019        dao->ops->commit_write(dao);
1020        return 0;
1021}
1022
1023static int atc_line_front_unmute(struct ct_atc *atc, unsigned char state)
1024{
1025        return atc_daio_unmute(atc, state, LINEO1);
1026}
1027
1028static int atc_line_surround_unmute(struct ct_atc *atc, unsigned char state)
1029{
1030        return atc_daio_unmute(atc, state, LINEO2);
1031}
1032
1033static int atc_line_clfe_unmute(struct ct_atc *atc, unsigned char state)
1034{
1035        return atc_daio_unmute(atc, state, LINEO3);
1036}
1037
1038static int atc_line_rear_unmute(struct ct_atc *atc, unsigned char state)
1039{
1040        return atc_daio_unmute(atc, state, LINEO4);
1041}
1042
1043static int atc_line_in_unmute(struct ct_atc *atc, unsigned char state)
1044{
1045        return atc_daio_unmute(atc, state, LINEIM);
1046}
1047
1048static int atc_spdif_out_unmute(struct ct_atc *atc, unsigned char state)
1049{
1050        return atc_daio_unmute(atc, state, SPDIFOO);
1051}
1052
1053static int atc_spdif_in_unmute(struct ct_atc *atc, unsigned char state)
1054{
1055        return atc_daio_unmute(atc, state, SPDIFIO);
1056}
1057
1058static int atc_spdif_out_get_status(struct ct_atc *atc, unsigned int *status)
1059{
1060        return atc_dao_get_status(atc, status, SPDIFOO);
1061}
1062
1063static int atc_spdif_out_set_status(struct ct_atc *atc, unsigned int status)
1064{
1065        return atc_dao_set_status(atc, status, SPDIFOO);
1066}
1067
1068static int atc_spdif_out_passthru(struct ct_atc *atc, unsigned char state)
1069{
1070        struct dao_desc da_dsc = {0};
1071        struct dao *dao;
1072        int err;
1073        struct ct_mixer *mixer = atc->mixer;
1074        struct rsc *rscs[2] = {NULL};
1075        unsigned int spos = 0;
1076
1077        mutex_lock(&atc->atc_mutex);
1078        dao = container_of(atc->daios[SPDIFOO], struct dao, daio);
1079        da_dsc.msr = state ? 1 : atc->msr;
1080        da_dsc.passthru = state ? 1 : 0;
1081        err = dao->ops->reinit(dao, &da_dsc);
1082        if (state) {
1083                spos = IEC958_DEFAULT_CON;
1084        } else {
1085                mixer->get_output_ports(mixer, MIX_SPDIF_OUT,
1086                                        &rscs[0], &rscs[1]);
1087                dao->ops->set_left_input(dao, rscs[0]);
1088                dao->ops->set_right_input(dao, rscs[1]);
1089                /* Restore PLL to atc->rsr if needed. */
1090                if (atc->pll_rate != atc->rsr)
1091                        err = atc_pll_init(atc, atc->rsr);
1092        }
1093        dao->ops->set_spos(dao, spos);
1094        dao->ops->commit_write(dao);
1095        mutex_unlock(&atc->atc_mutex);
1096
1097        return err;
1098}
1099
1100static int atc_release_resources(struct ct_atc *atc)
1101{
1102        int i;
1103        struct daio_mgr *daio_mgr = NULL;
1104        struct dao *dao = NULL;
1105        struct dai *dai = NULL;
1106        struct daio *daio = NULL;
1107        struct sum_mgr *sum_mgr = NULL;
1108        struct src_mgr *src_mgr = NULL;
1109        struct srcimp_mgr *srcimp_mgr = NULL;
1110        struct srcimp *srcimp = NULL;
1111        struct ct_mixer *mixer = NULL;
1112
1113        /* disconnect internal mixer objects */
1114        if (atc->mixer) {
1115                mixer = atc->mixer;
1116                mixer->set_input_left(mixer, MIX_LINE_IN, NULL);
1117                mixer->set_input_right(mixer, MIX_LINE_IN, NULL);
1118                mixer->set_input_left(mixer, MIX_MIC_IN, NULL);
1119                mixer->set_input_right(mixer, MIX_MIC_IN, NULL);
1120                mixer->set_input_left(mixer, MIX_SPDIF_IN, NULL);
1121                mixer->set_input_right(mixer, MIX_SPDIF_IN, NULL);
1122        }
1123
1124        if (atc->daios) {
1125                daio_mgr = (struct daio_mgr *)atc->rsc_mgrs[DAIO];
1126                for (i = 0; i < atc->n_daio; i++) {
1127                        daio = atc->daios[i];
1128                        if (daio->type < LINEIM) {
1129                                dao = container_of(daio, struct dao, daio);
1130                                dao->ops->clear_left_input(dao);
1131                                dao->ops->clear_right_input(dao);
1132                        } else {
1133                                dai = container_of(daio, struct dai, daio);
1134                                /* some thing to do for dai ... */
1135                        }
1136                        daio_mgr->put_daio(daio_mgr, daio);
1137                }
1138                kfree(atc->daios);
1139                atc->daios = NULL;
1140        }
1141
1142        if (atc->pcm) {
1143                sum_mgr = atc->rsc_mgrs[SUM];
1144                for (i = 0; i < atc->n_pcm; i++)
1145                        sum_mgr->put_sum(sum_mgr, atc->pcm[i]);
1146
1147                kfree(atc->pcm);
1148                atc->pcm = NULL;
1149        }
1150
1151        if (atc->srcs) {
1152                src_mgr = atc->rsc_mgrs[SRC];
1153                for (i = 0; i < atc->n_src; i++)
1154                        src_mgr->put_src(src_mgr, atc->srcs[i]);
1155
1156                kfree(atc->srcs);
1157                atc->srcs = NULL;
1158        }
1159
1160        if (atc->srcimps) {
1161                srcimp_mgr = atc->rsc_mgrs[SRCIMP];
1162                for (i = 0; i < atc->n_srcimp; i++) {
1163                        srcimp = atc->srcimps[i];
1164                        srcimp->ops->unmap(srcimp);
1165                        srcimp_mgr->put_srcimp(srcimp_mgr, atc->srcimps[i]);
1166                }
1167                kfree(atc->srcimps);
1168                atc->srcimps = NULL;
1169        }
1170
1171        return 0;
1172}
1173
1174static int ct_atc_destroy(struct ct_atc *atc)
1175{
1176        int i = 0;
1177
1178        if (!atc)
1179                return 0;
1180
1181        if (atc->timer) {
1182                ct_timer_free(atc->timer);
1183                atc->timer = NULL;
1184        }
1185
1186        atc_release_resources(atc);
1187
1188        /* Destroy internal mixer objects */
1189        if (atc->mixer)
1190                ct_mixer_destroy(atc->mixer);
1191
1192        for (i = 0; i < NUM_RSCTYP; i++) {
1193                if (rsc_mgr_funcs[i].destroy && atc->rsc_mgrs[i])
1194                        rsc_mgr_funcs[i].destroy(atc->rsc_mgrs[i]);
1195
1196        }
1197
1198        if (atc->hw)
1199                destroy_hw_obj((struct hw *)atc->hw);
1200
1201        /* Destroy device virtual memory manager object */
1202        if (atc->vm) {
1203                ct_vm_destroy(atc->vm);
1204                atc->vm = NULL;
1205        }
1206
1207        kfree(atc);
1208
1209        return 0;
1210}
1211
1212static int atc_dev_free(struct snd_device *dev)
1213{
1214        struct ct_atc *atc = dev->device_data;
1215        return ct_atc_destroy(atc);
1216}
1217
1218static int __devinit atc_identify_card(struct ct_atc *atc, unsigned int ssid)
1219{
1220        const struct snd_pci_quirk *p;
1221        const struct snd_pci_quirk *list;
1222        u16 vendor_id, device_id;
1223
1224        switch (atc->chip_type) {
1225        case ATC20K1:
1226                atc->chip_name = "20K1";
1227                list = subsys_20k1_list;
1228                break;
1229        case ATC20K2:
1230                atc->chip_name = "20K2";
1231                list = subsys_20k2_list;
1232                break;
1233        default:
1234                return -ENOENT;
1235        }
1236        if (ssid) {
1237                vendor_id = ssid >> 16;
1238                device_id = ssid & 0xffff;
1239        } else {
1240                vendor_id = atc->pci->subsystem_vendor;
1241                device_id = atc->pci->subsystem_device;
1242        }
1243        p = snd_pci_quirk_lookup_id(vendor_id, device_id, list);
1244        if (p) {
1245                if (p->value < 0) {
1246                        printk(KERN_ERR "ctxfi: "
1247                               "Device %04x:%04x is black-listed\n",
1248                               vendor_id, device_id);
1249                        return -ENOENT;
1250                }
1251                atc->model = p->value;
1252        } else {
1253                if (atc->chip_type == ATC20K1)
1254                        atc->model = CT20K1_UNKNOWN;
1255                else
1256                        atc->model = CT20K2_UNKNOWN;
1257        }
1258        atc->model_name = ct_subsys_name[atc->model];
1259        snd_printd("ctxfi: chip %s model %s (%04x:%04x) is found\n",
1260                   atc->chip_name, atc->model_name,
1261                   vendor_id, device_id);
1262        return 0;
1263}
1264
1265int __devinit ct_atc_create_alsa_devs(struct ct_atc *atc)
1266{
1267        enum CTALSADEVS i;
1268        int err;
1269
1270        alsa_dev_funcs[MIXER].public_name = atc->chip_name;
1271
1272        for (i = 0; i < NUM_CTALSADEVS; i++) {
1273                if (!alsa_dev_funcs[i].create)
1274                        continue;
1275
1276                err = alsa_dev_funcs[i].create(atc, i,
1277                                alsa_dev_funcs[i].public_name);
1278                if (err) {
1279                        printk(KERN_ERR "ctxfi: "
1280                               "Creating alsa device %d failed!\n", i);
1281                        return err;
1282                }
1283        }
1284
1285        return 0;
1286}
1287
1288static int __devinit atc_create_hw_devs(struct ct_atc *atc)
1289{
1290        struct hw *hw;
1291        struct card_conf info = {0};
1292        int i, err;
1293
1294        err = create_hw_obj(atc->pci, atc->chip_type, atc->model, &hw);
1295        if (err) {
1296                printk(KERN_ERR "Failed to create hw obj!!!\n");
1297                return err;
1298        }
1299        atc->hw = hw;
1300
1301        /* Initialize card hardware. */
1302        info.rsr = atc->rsr;
1303        info.msr = atc->msr;
1304        info.vm_pgt_phys = atc_get_ptp_phys(atc, 0);
1305        err = hw->card_init(hw, &info);
1306        if (err < 0)
1307                return err;
1308
1309        for (i = 0; i < NUM_RSCTYP; i++) {
1310                if (!rsc_mgr_funcs[i].create)
1311                        continue;
1312
1313                err = rsc_mgr_funcs[i].create(atc->hw, &atc->rsc_mgrs[i]);
1314                if (err) {
1315                        printk(KERN_ERR "ctxfi: "
1316                               "Failed to create rsc_mgr %d!!!\n", i);
1317                        return err;
1318                }
1319        }
1320
1321        return 0;
1322}
1323
1324static int atc_get_resources(struct ct_atc *atc)
1325{
1326        struct daio_desc da_desc = {0};
1327        struct daio_mgr *daio_mgr;
1328        struct src_desc src_dsc = {0};
1329        struct src_mgr *src_mgr;
1330        struct srcimp_desc srcimp_dsc = {0};
1331        struct srcimp_mgr *srcimp_mgr;
1332        struct sum_desc sum_dsc = {0};
1333        struct sum_mgr *sum_mgr;
1334        int err, i;
1335
1336        atc->daios = kzalloc(sizeof(void *)*(DAIONUM), GFP_KERNEL);
1337        if (!atc->daios)
1338                return -ENOMEM;
1339
1340        atc->srcs = kzalloc(sizeof(void *)*(2*2), GFP_KERNEL);
1341        if (!atc->srcs)
1342                return -ENOMEM;
1343
1344        atc->srcimps = kzalloc(sizeof(void *)*(2*2), GFP_KERNEL);
1345        if (!atc->srcimps)
1346                return -ENOMEM;
1347
1348        atc->pcm = kzalloc(sizeof(void *)*(2*4), GFP_KERNEL);
1349        if (!atc->pcm)
1350                return -ENOMEM;
1351
1352        daio_mgr = (struct daio_mgr *)atc->rsc_mgrs[DAIO];
1353        da_desc.msr = atc->msr;
1354        for (i = 0, atc->n_daio = 0; i < DAIONUM-1; i++) {
1355                da_desc.type = i;
1356                err = daio_mgr->get_daio(daio_mgr, &da_desc,
1357                                        (struct daio **)&atc->daios[i]);
1358                if (err) {
1359                        printk(KERN_ERR "ctxfi: Failed to get DAIO "
1360                                        "resource %d!!!\n", i);
1361                        return err;
1362                }
1363                atc->n_daio++;
1364        }
1365        if (atc->model == CTSB073X)
1366                da_desc.type = SPDIFI1;
1367        else
1368                da_desc.type = SPDIFIO;
1369        err = daio_mgr->get_daio(daio_mgr, &da_desc,
1370                                (struct daio **)&atc->daios[i]);
1371        if (err) {
1372                printk(KERN_ERR "ctxfi: Failed to get S/PDIF-in resource!!!\n");
1373                return err;
1374        }
1375        atc->n_daio++;
1376
1377        src_mgr = atc->rsc_mgrs[SRC];
1378        src_dsc.multi = 1;
1379        src_dsc.msr = atc->msr;
1380        src_dsc.mode = ARCRW;
1381        for (i = 0, atc->n_src = 0; i < (2*2); i++) {
1382                err = src_mgr->get_src(src_mgr, &src_dsc,
1383                                        (struct src **)&atc->srcs[i]);
1384                if (err)
1385                        return err;
1386
1387                atc->n_src++;
1388        }
1389
1390        srcimp_mgr = atc->rsc_mgrs[SRCIMP];
1391        srcimp_dsc.msr = 8; /* SRCIMPs for S/PDIFIn SRT */
1392        for (i = 0, atc->n_srcimp = 0; i < (2*1); i++) {
1393                err = srcimp_mgr->get_srcimp(srcimp_mgr, &srcimp_dsc,
1394                                        (struct srcimp **)&atc->srcimps[i]);
1395                if (err)
1396                        return err;
1397
1398                atc->n_srcimp++;
1399        }
1400        srcimp_dsc.msr = 8; /* SRCIMPs for LINE/MICIn SRT */
1401        for (i = 0; i < (2*1); i++) {
1402                err = srcimp_mgr->get_srcimp(srcimp_mgr, &srcimp_dsc,
1403                                (struct srcimp **)&atc->srcimps[2*1+i]);
1404                if (err)
1405                        return err;
1406
1407                atc->n_srcimp++;
1408        }
1409
1410        sum_mgr = atc->rsc_mgrs[SUM];
1411        sum_dsc.msr = atc->msr;
1412        for (i = 0, atc->n_pcm = 0; i < (2*4); i++) {
1413                err = sum_mgr->get_sum(sum_mgr, &sum_dsc,
1414                                        (struct sum **)&atc->pcm[i]);
1415                if (err)
1416                        return err;
1417
1418                atc->n_pcm++;
1419        }
1420
1421        return 0;
1422}
1423
1424static void
1425atc_connect_dai(struct src_mgr *src_mgr, struct dai *dai,
1426                struct src **srcs, struct srcimp **srcimps)
1427{
1428        struct rsc *rscs[2] = {NULL};
1429        struct src *src;
1430        struct srcimp *srcimp;
1431        int i = 0;
1432
1433        rscs[0] = &dai->daio.rscl;
1434        rscs[1] = &dai->daio.rscr;
1435        for (i = 0; i < 2; i++) {
1436                src = srcs[i];
1437                srcimp = srcimps[i];
1438                srcimp->ops->map(srcimp, src, rscs[i]);
1439                src_mgr->src_disable(src_mgr, src);
1440        }
1441
1442        src_mgr->commit_write(src_mgr); /* Actually disable SRCs */
1443
1444        src = srcs[0];
1445        src->ops->set_pm(src, 1);
1446        for (i = 0; i < 2; i++) {
1447                src = srcs[i];
1448                src->ops->set_state(src, SRC_STATE_RUN);
1449                src->ops->commit_write(src);
1450                src_mgr->src_enable_s(src_mgr, src);
1451        }
1452
1453        dai->ops->set_srt_srcl(dai, &(srcs[0]->rsc));
1454        dai->ops->set_srt_srcr(dai, &(srcs[1]->rsc));
1455
1456        dai->ops->set_enb_src(dai, 1);
1457        dai->ops->set_enb_srt(dai, 1);
1458        dai->ops->commit_write(dai);
1459
1460        src_mgr->commit_write(src_mgr); /* Synchronously enable SRCs */
1461}
1462
1463static void atc_connect_resources(struct ct_atc *atc)
1464{
1465        struct dai *dai;
1466        struct dao *dao;
1467        struct src *src;
1468        struct sum *sum;
1469        struct ct_mixer *mixer;
1470        struct rsc *rscs[2] = {NULL};
1471        int i, j;
1472
1473        mixer = atc->mixer;
1474
1475        for (i = MIX_WAVE_FRONT, j = LINEO1; i <= MIX_SPDIF_OUT; i++, j++) {
1476                mixer->get_output_ports(mixer, i, &rscs[0], &rscs[1]);
1477                dao = container_of(atc->daios[j], struct dao, daio);
1478                dao->ops->set_left_input(dao, rscs[0]);
1479                dao->ops->set_right_input(dao, rscs[1]);
1480        }
1481
1482        dai = container_of(atc->daios[LINEIM], struct dai, daio);
1483        atc_connect_dai(atc->rsc_mgrs[SRC], dai,
1484                        (struct src **)&atc->srcs[2],
1485                        (struct srcimp **)&atc->srcimps[2]);
1486        src = atc->srcs[2];
1487        mixer->set_input_left(mixer, MIX_LINE_IN, &src->rsc);
1488        src = atc->srcs[3];
1489        mixer->set_input_right(mixer, MIX_LINE_IN, &src->rsc);
1490
1491        dai = container_of(atc->daios[SPDIFIO], struct dai, daio);
1492        atc_connect_dai(atc->rsc_mgrs[SRC], dai,
1493                        (struct src **)&atc->srcs[0],
1494                        (struct srcimp **)&atc->srcimps[0]);
1495
1496        src = atc->srcs[0];
1497        mixer->set_input_left(mixer, MIX_SPDIF_IN, &src->rsc);
1498        src = atc->srcs[1];
1499        mixer->set_input_right(mixer, MIX_SPDIF_IN, &src->rsc);
1500
1501        for (i = MIX_PCMI_FRONT, j = 0; i <= MIX_PCMI_SURROUND; i++, j += 2) {
1502                sum = atc->pcm[j];
1503                mixer->set_input_left(mixer, i, &sum->rsc);
1504                sum = atc->pcm[j+1];
1505                mixer->set_input_right(mixer, i, &sum->rsc);
1506        }
1507}
1508
1509#ifdef CONFIG_PM
1510static int atc_suspend(struct ct_atc *atc, pm_message_t state)
1511{
1512        int i;
1513        struct hw *hw = atc->hw;
1514
1515        snd_power_change_state(atc->card, SNDRV_CTL_POWER_D3hot);
1516
1517        for (i = FRONT; i < NUM_PCMS; i++) {
1518                if (!atc->pcms[i])
1519                        continue;
1520
1521                snd_pcm_suspend_all(atc->pcms[i]);
1522        }
1523
1524        atc_release_resources(atc);
1525
1526        hw->suspend(hw, state);
1527
1528        return 0;
1529}
1530
1531static int atc_hw_resume(struct ct_atc *atc)
1532{
1533        struct hw *hw = atc->hw;
1534        struct card_conf info = {0};
1535
1536        /* Re-initialize card hardware. */
1537        info.rsr = atc->rsr;
1538        info.msr = atc->msr;
1539        info.vm_pgt_phys = atc_get_ptp_phys(atc, 0);
1540        return hw->resume(hw, &info);
1541}
1542
1543static int atc_resources_resume(struct ct_atc *atc)
1544{
1545        struct ct_mixer *mixer;
1546        int err = 0;
1547
1548        /* Get resources */
1549        err = atc_get_resources(atc);
1550        if (err < 0) {
1551                atc_release_resources(atc);
1552                return err;
1553        }
1554
1555        /* Build topology */
1556        atc_connect_resources(atc);
1557
1558        mixer = atc->mixer;
1559        mixer->resume(mixer);
1560
1561        return 0;
1562}
1563
1564static int atc_resume(struct ct_atc *atc)
1565{
1566        int err = 0;
1567
1568        /* Do hardware resume. */
1569        err = atc_hw_resume(atc);
1570        if (err < 0) {
1571                printk(KERN_ERR "ctxfi: pci_enable_device failed, "
1572                       "disabling device\n");
1573                snd_card_disconnect(atc->card);
1574                return err;
1575        }
1576
1577        err = atc_resources_resume(atc);
1578        if (err < 0)
1579                return err;
1580
1581        snd_power_change_state(atc->card, SNDRV_CTL_POWER_D0);
1582
1583        return 0;
1584}
1585#endif
1586
1587static struct ct_atc atc_preset __devinitdata = {
1588        .map_audio_buffer = ct_map_audio_buffer,
1589        .unmap_audio_buffer = ct_unmap_audio_buffer,
1590        .pcm_playback_prepare = atc_pcm_playback_prepare,
1591        .pcm_release_resources = atc_pcm_release_resources,
1592        .pcm_playback_start = atc_pcm_playback_start,
1593        .pcm_playback_stop = atc_pcm_stop,
1594        .pcm_playback_position = atc_pcm_playback_position,
1595        .pcm_capture_prepare = atc_pcm_capture_prepare,
1596        .pcm_capture_start = atc_pcm_capture_start,
1597        .pcm_capture_stop = atc_pcm_stop,
1598        .pcm_capture_position = atc_pcm_capture_position,
1599        .spdif_passthru_playback_prepare = spdif_passthru_playback_prepare,
1600        .get_ptp_phys = atc_get_ptp_phys,
1601        .select_line_in = atc_select_line_in,
1602        .select_mic_in = atc_select_mic_in,
1603        .select_digit_io = atc_select_digit_io,
1604        .line_front_unmute = atc_line_front_unmute,
1605        .line_surround_unmute = atc_line_surround_unmute,
1606        .line_clfe_unmute = atc_line_clfe_unmute,
1607        .line_rear_unmute = atc_line_rear_unmute,
1608        .line_in_unmute = atc_line_in_unmute,
1609        .spdif_out_unmute = atc_spdif_out_unmute,
1610        .spdif_in_unmute = atc_spdif_in_unmute,
1611        .spdif_out_get_status = atc_spdif_out_get_status,
1612        .spdif_out_set_status = atc_spdif_out_set_status,
1613        .spdif_out_passthru = atc_spdif_out_passthru,
1614        .have_digit_io_switch = atc_have_digit_io_switch,
1615#ifdef CONFIG_PM
1616        .suspend = atc_suspend,
1617        .resume = atc_resume,
1618#endif
1619};
1620
1621/**
1622 *  ct_atc_create - create and initialize a hardware manager
1623 *  @card: corresponding alsa card object
1624 *  @pci: corresponding kernel pci device object
1625 *  @ratc: return created object address in it
1626 *
1627 *  Creates and initializes a hardware manager.
1628 *
1629 *  Creates kmallocated ct_atc structure. Initializes hardware.
1630 *  Returns 0 if suceeds, or negative error code if fails.
1631 */
1632
1633int __devinit ct_atc_create(struct snd_card *card, struct pci_dev *pci,
1634                            unsigned int rsr, unsigned int msr,
1635                            int chip_type, unsigned int ssid,
1636                            struct ct_atc **ratc)
1637{
1638        struct ct_atc *atc;
1639        static struct snd_device_ops ops = {
1640                .dev_free = atc_dev_free,
1641        };
1642        int err;
1643
1644        *ratc = NULL;
1645
1646        atc = kzalloc(sizeof(*atc), GFP_KERNEL);
1647        if (!atc)
1648                return -ENOMEM;
1649
1650        /* Set operations */
1651        *atc = atc_preset;
1652
1653        atc->card = card;
1654        atc->pci = pci;
1655        atc->rsr = rsr;
1656        atc->msr = msr;
1657        atc->chip_type = chip_type;
1658
1659        mutex_init(&atc->atc_mutex);
1660
1661        /* Find card model */
1662        err = atc_identify_card(atc, ssid);
1663        if (err < 0) {
1664                printk(KERN_ERR "ctatc: Card not recognised\n");
1665                goto error1;
1666        }
1667
1668        /* Set up device virtual memory management object */
1669        err = ct_vm_create(&atc->vm, pci);
1670        if (err < 0)
1671                goto error1;
1672
1673        /* Create all atc hw devices */
1674        err = atc_create_hw_devs(atc);
1675        if (err < 0)
1676                goto error1;
1677
1678        err = ct_mixer_create(atc, (struct ct_mixer **)&atc->mixer);
1679        if (err) {
1680                printk(KERN_ERR "ctxfi: Failed to create mixer obj!!!\n");
1681                goto error1;
1682        }
1683
1684        /* Get resources */
1685        err = atc_get_resources(atc);
1686        if (err < 0)
1687                goto error1;
1688
1689        /* Build topology */
1690        atc_connect_resources(atc);
1691
1692        atc->timer = ct_timer_new(atc);
1693        if (!atc->timer)
1694                goto error1;
1695
1696        err = snd_device_new(card, SNDRV_DEV_LOWLEVEL, atc, &ops);
1697        if (err < 0)
1698                goto error1;
1699
1700        snd_card_set_dev(card, &pci->dev);
1701
1702        *ratc = atc;
1703        return 0;
1704
1705error1:
1706        ct_atc_destroy(atc);
1707        printk(KERN_ERR "ctxfi: Something wrong!!!\n");
1708        return err;
1709}
1710