linux/include/sound/cs8403.h
<<
>>
Prefs
   1#ifndef __SOUND_CS8403_H
   2#define __SOUND_CS8403_H
   3
   4/*
   5 *  Routines for Cirrus Logic CS8403/CS8404A IEC958 (S/PDIF) Transmitter
   6 *  Copyright (c) by Jaroslav Kysela <perex@perex.cz>,
   7 *                   Takashi Iwai <tiwai@suse.de>
   8 *
   9 *
  10 *   This program is free software; you can redistribute it and/or modify
  11 *   it under the terms of the GNU General Public License as published by
  12 *   the Free Software Foundation; either version 2 of the License, or
  13 *   (at your option) any later version.
  14 *
  15 *   This program is distributed in the hope that it will be useful,
  16 *   but WITHOUT ANY WARRANTY; without even the implied warranty of
  17 *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  18 *   GNU General Public License for more details.
  19 *
  20 *   You should have received a copy of the GNU General Public License
  21 *   along with this program; if not, write to the Free Software
  22 *   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
  23 *
  24 */
  25
  26#ifdef SND_CS8403
  27
  28#ifndef SND_CS8403_DECL
  29#define SND_CS8403_DECL static
  30#endif
  31#ifndef SND_CS8403_DECODE
  32#define SND_CS8403_DECODE snd_cs8403_decode_spdif_bits
  33#endif
  34#ifndef SND_CS8403_ENCODE
  35#define SND_CS8403_ENCODE snd_cs8403_encode_spdif_bits
  36#endif
  37
  38
  39SND_CS8403_DECL void SND_CS8403_DECODE(struct snd_aes_iec958 *diga, unsigned char bits)
  40{
  41        if (bits & 0x01) {      /* consumer */
  42                if (!(bits & 0x02))
  43                        diga->status[0] |= IEC958_AES0_NONAUDIO;
  44                if (!(bits & 0x08))
  45                        diga->status[0] |= IEC958_AES0_CON_NOT_COPYRIGHT;
  46                switch (bits & 0x10) {
  47                case 0x10: diga->status[0] |= IEC958_AES0_CON_EMPHASIS_NONE; break;
  48                case 0x00: diga->status[0] |= IEC958_AES0_CON_EMPHASIS_5015; break;
  49                }
  50                if (!(bits & 0x80))
  51                        diga->status[1] |= IEC958_AES1_CON_ORIGINAL;
  52                switch (bits & 0x60) {
  53                case 0x00: diga->status[1] |= IEC958_AES1_CON_MAGNETIC_ID; break;
  54                case 0x20: diga->status[1] |= IEC958_AES1_CON_DIGDIGCONV_ID; break;
  55                case 0x40: diga->status[1] |= IEC958_AES1_CON_LASEROPT_ID; break;
  56                case 0x60: diga->status[1] |= IEC958_AES1_CON_GENERAL; break;
  57                }
  58                switch (bits & 0x06) {
  59                case 0x00: diga->status[3] |= IEC958_AES3_CON_FS_44100; break;
  60                case 0x02: diga->status[3] |= IEC958_AES3_CON_FS_48000; break;
  61                case 0x04: diga->status[3] |= IEC958_AES3_CON_FS_32000; break;
  62                }
  63        } else {
  64                diga->status[0] = IEC958_AES0_PROFESSIONAL;
  65                switch (bits & 0x18) {
  66                case 0x00: diga->status[0] |= IEC958_AES0_PRO_FS_32000; break;
  67                case 0x10: diga->status[0] |= IEC958_AES0_PRO_FS_44100; break;
  68                case 0x08: diga->status[0] |= IEC958_AES0_PRO_FS_48000; break;
  69                case 0x18: diga->status[0] |= IEC958_AES0_PRO_FS_NOTID; break;
  70                }
  71                switch (bits & 0x60) {
  72                case 0x20: diga->status[0] |= IEC958_AES0_PRO_EMPHASIS_NONE; break;
  73                case 0x40: diga->status[0] |= IEC958_AES0_PRO_EMPHASIS_5015; break;
  74                case 0x00: diga->status[0] |= IEC958_AES0_PRO_EMPHASIS_CCITT; break;
  75                case 0x60: diga->status[0] |= IEC958_AES0_PRO_EMPHASIS_NOTID; break;
  76                }
  77                if (bits & 0x80)
  78                        diga->status[1] |= IEC958_AES1_PRO_MODE_STEREOPHONIC;
  79        }
  80}
  81
  82SND_CS8403_DECL unsigned char SND_CS8403_ENCODE(struct snd_aes_iec958 *diga)
  83{
  84        unsigned char bits;
  85
  86        if (!(diga->status[0] & IEC958_AES0_PROFESSIONAL)) {
  87                bits = 0x01;    /* consumer mode */
  88                if (diga->status[0] & IEC958_AES0_NONAUDIO)
  89                        bits &= ~0x02;
  90                else
  91                        bits |= 0x02;
  92                if (diga->status[0] & IEC958_AES0_CON_NOT_COPYRIGHT)
  93                        bits &= ~0x08;
  94                else
  95                        bits |= 0x08;
  96                switch (diga->status[0] & IEC958_AES0_CON_EMPHASIS) {
  97                default:
  98                case IEC958_AES0_CON_EMPHASIS_NONE: bits |= 0x10; break;
  99                case IEC958_AES0_CON_EMPHASIS_5015: bits |= 0x00; break;
 100                }
 101                if (diga->status[1] & IEC958_AES1_CON_ORIGINAL)
 102                        bits &= ~0x80;
 103                else
 104                        bits |= 0x80;
 105                if ((diga->status[1] & IEC958_AES1_CON_CATEGORY) == IEC958_AES1_CON_GENERAL)
 106                        bits |= 0x60;
 107                else {
 108                        switch(diga->status[1] & IEC958_AES1_CON_MAGNETIC_MASK) {
 109                        case IEC958_AES1_CON_MAGNETIC_ID:
 110                                bits |= 0x00; break;
 111                        case IEC958_AES1_CON_DIGDIGCONV_ID:
 112                                bits |= 0x20; break;
 113                        default:
 114                        case IEC958_AES1_CON_LASEROPT_ID:
 115                                bits |= 0x40; break;
 116                        }
 117                }
 118                switch (diga->status[3] & IEC958_AES3_CON_FS) {
 119                default:
 120                case IEC958_AES3_CON_FS_44100: bits |= 0x00; break;
 121                case IEC958_AES3_CON_FS_48000: bits |= 0x02; break;
 122                case IEC958_AES3_CON_FS_32000: bits |= 0x04; break;
 123                }
 124        } else {
 125                bits = 0x00;    /* professional mode */
 126                if (diga->status[0] & IEC958_AES0_NONAUDIO)
 127                        bits &= ~0x02;
 128                else
 129                        bits |= 0x02;
 130                /* CHECKME: I'm not sure about the bit order in val here */
 131                switch (diga->status[0] & IEC958_AES0_PRO_FS) {
 132                case IEC958_AES0_PRO_FS_32000:  bits |= 0x00; break;
 133                case IEC958_AES0_PRO_FS_44100:  bits |= 0x10; break;    /* 44.1kHz */
 134                case IEC958_AES0_PRO_FS_48000:  bits |= 0x08; break;    /* 48kHz */
 135                default:
 136                case IEC958_AES0_PRO_FS_NOTID: bits |= 0x18; break;
 137                }
 138                switch (diga->status[0] & IEC958_AES0_PRO_EMPHASIS) {
 139                case IEC958_AES0_PRO_EMPHASIS_NONE: bits |= 0x20; break;
 140                case IEC958_AES0_PRO_EMPHASIS_5015: bits |= 0x40; break;
 141                case IEC958_AES0_PRO_EMPHASIS_CCITT: bits |= 0x00; break;
 142                default:
 143                case IEC958_AES0_PRO_EMPHASIS_NOTID: bits |= 0x60; break;
 144                }
 145                switch (diga->status[1] & IEC958_AES1_PRO_MODE) {
 146                case IEC958_AES1_PRO_MODE_TWO:
 147                case IEC958_AES1_PRO_MODE_STEREOPHONIC: bits |= 0x00; break;
 148                default: bits |= 0x80; break;
 149                }
 150        }
 151        return bits;
 152}
 153
 154#endif /* SND_CS8403 */
 155
 156#ifdef SND_CS8404
 157
 158#ifndef SND_CS8404_DECL
 159#define SND_CS8404_DECL static
 160#endif
 161#ifndef SND_CS8404_DECODE
 162#define SND_CS8404_DECODE snd_cs8404_decode_spdif_bits
 163#endif
 164#ifndef SND_CS8404_ENCODE
 165#define SND_CS8404_ENCODE snd_cs8404_encode_spdif_bits
 166#endif
 167
 168
 169SND_CS8404_DECL void SND_CS8404_DECODE(struct snd_aes_iec958 *diga, unsigned char bits)
 170{
 171        if (bits & 0x10) {      /* consumer */
 172                if (!(bits & 0x20))
 173                        diga->status[0] |= IEC958_AES0_CON_NOT_COPYRIGHT;
 174                if (!(bits & 0x40))
 175                        diga->status[0] |= IEC958_AES0_CON_EMPHASIS_5015;
 176                if (!(bits & 0x80))
 177                        diga->status[1] |= IEC958_AES1_CON_ORIGINAL;
 178                switch (bits & 0x03) {
 179                case 0x00: diga->status[1] |= IEC958_AES1_CON_DAT; break;
 180                case 0x03: diga->status[1] |= IEC958_AES1_CON_GENERAL; break;
 181                }
 182                switch (bits & 0x06) {
 183                case 0x02: diga->status[3] |= IEC958_AES3_CON_FS_32000; break;
 184                case 0x04: diga->status[3] |= IEC958_AES3_CON_FS_48000; break;
 185                case 0x06: diga->status[3] |= IEC958_AES3_CON_FS_44100; break;
 186                }
 187        } else {
 188                diga->status[0] = IEC958_AES0_PROFESSIONAL;
 189                if (!(bits & 0x04))
 190                        diga->status[0] |= IEC958_AES0_NONAUDIO;
 191                switch (bits & 0x60) {
 192                case 0x00: diga->status[0] |= IEC958_AES0_PRO_FS_32000; break;
 193                case 0x40: diga->status[0] |= IEC958_AES0_PRO_FS_44100; break;
 194                case 0x20: diga->status[0] |= IEC958_AES0_PRO_FS_48000; break;
 195                case 0x60: diga->status[0] |= IEC958_AES0_PRO_FS_NOTID; break;
 196                }
 197                switch (bits & 0x03) {
 198                case 0x02: diga->status[0] |= IEC958_AES0_PRO_EMPHASIS_NONE; break;
 199                case 0x01: diga->status[0] |= IEC958_AES0_PRO_EMPHASIS_5015; break;
 200                case 0x00: diga->status[0] |= IEC958_AES0_PRO_EMPHASIS_CCITT; break;
 201                case 0x03: diga->status[0] |= IEC958_AES0_PRO_EMPHASIS_NOTID; break;
 202                }
 203                if (!(bits & 0x80))
 204                        diga->status[1] |= IEC958_AES1_PRO_MODE_STEREOPHONIC;
 205        }
 206}
 207
 208SND_CS8404_DECL unsigned char SND_CS8404_ENCODE(struct snd_aes_iec958 *diga)
 209{
 210        unsigned char bits;
 211
 212        if (!(diga->status[0] & IEC958_AES0_PROFESSIONAL)) {
 213                bits = 0x10;    /* consumer mode */
 214                if (!(diga->status[0] & IEC958_AES0_CON_NOT_COPYRIGHT))
 215                        bits |= 0x20;
 216                if ((diga->status[0] & IEC958_AES0_CON_EMPHASIS) == IEC958_AES0_CON_EMPHASIS_NONE)
 217                        bits |= 0x40;
 218                if (!(diga->status[1] & IEC958_AES1_CON_ORIGINAL))
 219                        bits |= 0x80;
 220                if ((diga->status[1] & IEC958_AES1_CON_CATEGORY) == IEC958_AES1_CON_GENERAL)
 221                        bits |= 0x03;
 222                switch (diga->status[3] & IEC958_AES3_CON_FS) {
 223                default:
 224                case IEC958_AES3_CON_FS_44100: bits |= 0x06; break;
 225                case IEC958_AES3_CON_FS_48000: bits |= 0x04; break;
 226                case IEC958_AES3_CON_FS_32000: bits |= 0x02; break;
 227                }
 228        } else {
 229                bits = 0x00;    /* professional mode */
 230                if (!(diga->status[0] & IEC958_AES0_NONAUDIO))
 231                        bits |= 0x04;
 232                switch (diga->status[0] & IEC958_AES0_PRO_FS) {
 233                case IEC958_AES0_PRO_FS_32000:  bits |= 0x00; break;
 234                case IEC958_AES0_PRO_FS_44100:  bits |= 0x40; break;    /* 44.1kHz */
 235                case IEC958_AES0_PRO_FS_48000:  bits |= 0x20; break;    /* 48kHz */
 236                default:
 237                case IEC958_AES0_PRO_FS_NOTID:  bits |= 0x00; break;
 238                }
 239                switch (diga->status[0] & IEC958_AES0_PRO_EMPHASIS) {
 240                case IEC958_AES0_PRO_EMPHASIS_NONE: bits |= 0x02; break;
 241                case IEC958_AES0_PRO_EMPHASIS_5015: bits |= 0x01; break;
 242                case IEC958_AES0_PRO_EMPHASIS_CCITT: bits |= 0x00; break;
 243                default:
 244                case IEC958_AES0_PRO_EMPHASIS_NOTID: bits |= 0x03; break;
 245                }
 246                switch (diga->status[1] & IEC958_AES1_PRO_MODE) {
 247                case IEC958_AES1_PRO_MODE_TWO:
 248                case IEC958_AES1_PRO_MODE_STEREOPHONIC: bits |= 0x00; break;
 249                default: bits |= 0x80; break;
 250                }
 251        }
 252        return bits;
 253}
 254
 255#endif /* SND_CS8404 */
 256
 257#endif /* __SOUND_CS8403_H */
 258