vorbis.c
上传用户:wstnjxml
上传日期:2014-04-03
资源大小:7248k
文件大小:4k
源码类别:

Windows CE

开发平台:

C/C++

  1. /*****************************************************************************
  2.  *
  3.  * This program is free software ; you can redistribute it and/or modify
  4.  * it under the terms of the GNU General Public License as published by
  5.  * the Free Software Foundation; either version 2 of the License, or
  6.  * (at your option) any later version.
  7.  *
  8.  * This program is distributed in the hope that it will be useful,
  9.  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  10.  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  11.  * GNU General Public License for more details.
  12.  *
  13.  * You should have received a copy of the GNU General Public License
  14.  * along with this program; if not, write to the Free Software
  15.  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
  16.  *
  17.  * $Id: vorbis.c 543 2006-01-07 22:06:24Z picard $
  18.  *
  19.  * The Core Pocket Media Player
  20.  * Copyright (c) 2004-2005 Gabor Kovacs
  21.  *
  22.  ****************************************************************************/
  23. #include "../common/common.h"
  24. #include "vorbis.h"
  25. #include "tremor/ogg.h"
  26. #include "tremor/ivorbiscodec.h"
  27. // Vorbis audio codec
  28. typedef struct vorbis
  29. {
  30. codec Codec;
  31. vorbis_dsp_state DSP;
  32. vorbis_block Block;
  33. bool_t Inited;
  34. ogg_int32_t **PCM;
  35. int Samples;
  36. } vorbis;
  37. #define OGG_F_BITS 24
  38. #define OGG_F_ONE (1<<24)
  39. #define ogg_f_mul(a,b) (((a)>>12)*((b)>>12))
  40. #undef malloc
  41. void* _calloc(int n,int m)
  42. {
  43. void* p = malloc(n*m);
  44. if (p) memset(p,0,n*m);
  45. return p;
  46. }
  47. static int Flush(vorbis* p)
  48. {
  49. vorbis_synthesis_restart(&p->DSP);
  50. p->Samples = 0;
  51. return ERR_NONE;
  52. }
  53. static int UpdateInput(vorbis* p)
  54. {
  55. vorbis_block_clear(&p->Block);
  56. vorbis_dsp_clear(&p->DSP);
  57. if (p->Codec.In.Format.Type == PACKET_AUDIO)
  58. {
  59. vorbis_info* Info = (vorbis_info*)p->Codec.In.Format.Extra;
  60. if (Info)
  61. {
  62. vorbis_synthesis_init(&p->DSP,Info);
  63. vorbis_block_init(&p->DSP,&p->Block);
  64. p->Codec.In.Format.ByteRate = Info->bitrate_nominal >> 3;
  65. p->Codec.In.Format.Format.Audio.SampleRate = Info->rate;
  66. p->Codec.In.Format.Format.Audio.Channels = Info->channels;
  67. }
  68. PacketFormatPCM(&p->Codec.Out.Format,&p->Codec.In.Format,OGG_F_BITS+1);
  69. p->Codec.Out.Format.Format.Audio.Flags = PCM_PLANES;
  70. }
  71. return ERR_NONE;
  72. }
  73. static int Process(vorbis* p, const packet* Packet, const flowstate* State)
  74. {
  75. if (Packet)
  76. {
  77. if (Packet->Length != sizeof(ogg_packet))
  78. return ERR_INVALID_DATA;
  79. while (vorbis_synthesis(&p->Block,(ogg_packet*)Packet->Data[0],1)==0)
  80. {
  81. vorbis_synthesis_blockin(&p->DSP,&p->Block);
  82. p->Samples = vorbis_synthesis_pcmout(&p->DSP,&p->PCM);
  83. if (p->Samples)
  84. {
  85. p->Codec.Packet.RefTime = Packet->RefTime;
  86. p->Codec.Packet.Length = p->Samples * sizeof(ogg_int32_t);
  87. p->Codec.Packet.Data[0] = p->PCM[0];
  88. p->Codec.Packet.Data[1] = p->PCM[1];
  89. return ERR_NONE;
  90. }
  91. }
  92. }
  93. else
  94. if (p->Samples)
  95. {
  96. vorbis_synthesis_read(&p->DSP,p->Samples);
  97. p->Samples = 0;
  98. }
  99. return ERR_NEED_MORE_DATA;
  100. }
  101. static int Create(vorbis* p)
  102. {
  103. p->Codec.UpdateInput = (nodefunc)UpdateInput;
  104. p->Codec.Process = (packetprocess)Process;
  105. p->Codec.Flush = (nodefunc)Flush;
  106. return ERR_NONE;
  107. }
  108. static const nodedef VorbisV = 
  109. {
  110. sizeof(vorbis),
  111. VORBIS_V_ID,
  112. CODEC_CLASS,
  113. VORBIS_V_PRI,
  114. (nodecreate)Create,
  115. };
  116. static const nodedef VorbisA = 
  117. {
  118. sizeof(vorbis),
  119. VORBIS_A_ID,
  120. CODEC_CLASS,
  121. VORBIS_A_PRI,
  122. (nodecreate)Create,
  123. };
  124. void Vorbis_Init()
  125. {
  126. NodeRegisterClass(&VorbisV);
  127. NodeRegisterClass(&VorbisA);
  128. }
  129. void Vorbis_Done()
  130. {
  131. NodeUnRegisterClass(VORBIS_A_ID);
  132. NodeUnRegisterClass(VORBIS_V_ID);
  133. }