codec_builtin.c 19 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846
  1. /*
  2. * Asterisk -- An open source telephony toolkit.
  3. *
  4. * Copyright (C) 2014, Digium, Inc.
  5. *
  6. * Joshua Colp <jcolp@digium.com>
  7. *
  8. * See http://www.asterisk.org for more information about
  9. * the Asterisk project. Please do not directly contact
  10. * any of the maintainers of this project for assistance;
  11. * the project provides a web site, mailing lists and IRC
  12. * channels for your use.
  13. *
  14. * This program is free software, distributed under the terms of
  15. * the GNU General Public License Version 2. See the LICENSE file
  16. * at the top of the source tree.
  17. */
  18. /*! \file
  19. *
  20. * \brief Built-in supported codecs
  21. *
  22. * \author Joshua Colp <jcolp@digium.com>
  23. */
  24. /*** MODULEINFO
  25. <support_level>core</support_level>
  26. ***/
  27. #include "asterisk.h"
  28. ASTERISK_FILE_VERSION(__FILE__, "$Revision$")
  29. #include "asterisk/logger.h"
  30. #include "asterisk/astobj2.h"
  31. #include "asterisk/codec.h"
  32. #include "asterisk/format.h"
  33. #include "asterisk/format_cache.h"
  34. #include "asterisk/frame.h"
  35. enum frame_type {
  36. TYPE_HIGH, /* 0x0 */
  37. TYPE_LOW, /* 0x1 */
  38. TYPE_SILENCE, /* 0x2 */
  39. TYPE_DONTSEND /* 0x3 */
  40. };
  41. #define TYPE_MASK 0x3
  42. static int g723_len(unsigned char buf)
  43. {
  44. enum frame_type type = buf & TYPE_MASK;
  45. switch(type) {
  46. case TYPE_DONTSEND:
  47. return 0;
  48. break;
  49. case TYPE_SILENCE:
  50. return 4;
  51. break;
  52. case TYPE_HIGH:
  53. return 24;
  54. break;
  55. case TYPE_LOW:
  56. return 20;
  57. break;
  58. default:
  59. ast_log(LOG_WARNING, "Badly encoded frame (%u)\n", type);
  60. }
  61. return -1;
  62. }
  63. static int g723_samples(struct ast_frame *frame)
  64. {
  65. unsigned char *buf = frame->data.ptr;
  66. int pos = 0, samples = 0, res;
  67. while(pos < frame->datalen) {
  68. res = g723_len(buf[pos]);
  69. if (res <= 0)
  70. break;
  71. samples += 240;
  72. pos += res;
  73. }
  74. return samples;
  75. }
  76. static int g723_length(unsigned int samples)
  77. {
  78. return (samples / 240) * 20;
  79. }
  80. static struct ast_codec g723 = {
  81. .name = "g723",
  82. .description = "G.723.1",
  83. .type = AST_MEDIA_TYPE_AUDIO,
  84. .sample_rate = 8000,
  85. .minimum_ms = 30,
  86. .maximum_ms = 300,
  87. .default_ms = 30,
  88. .minimum_bytes = 20,
  89. .samples_count = g723_samples,
  90. .get_length = g723_length,
  91. };
  92. static int none_samples(struct ast_frame *frame)
  93. {
  94. return frame->datalen;
  95. }
  96. static int none_length(unsigned int samples) {
  97. return samples;
  98. }
  99. static struct ast_codec none = {
  100. .name = "none",
  101. .description = "<Null> codec",
  102. .type = AST_MEDIA_TYPE_AUDIO,
  103. .sample_rate = 8000, /* This must have some sample rate to prevent divide by 0 */
  104. .minimum_ms = 10,
  105. .maximum_ms = 150,
  106. .default_ms = 20,
  107. .minimum_bytes = 20,
  108. .samples_count = none_samples,
  109. .get_length = none_length,
  110. };
  111. static int ulaw_samples(struct ast_frame *frame)
  112. {
  113. return frame->datalen;
  114. }
  115. static int ulaw_length(unsigned int samples)
  116. {
  117. return samples;
  118. }
  119. static struct ast_codec ulaw = {
  120. .name = "ulaw",
  121. .description = "G.711 u-law",
  122. .type = AST_MEDIA_TYPE_AUDIO,
  123. .sample_rate = 8000,
  124. .minimum_ms = 10,
  125. .maximum_ms = 150,
  126. .default_ms = 20,
  127. .minimum_bytes = 80,
  128. .samples_count = ulaw_samples,
  129. .get_length = ulaw_length,
  130. .smooth = 1,
  131. };
  132. static struct ast_codec alaw = {
  133. .name = "alaw",
  134. .description = "G.711 a-law",
  135. .type = AST_MEDIA_TYPE_AUDIO,
  136. .sample_rate = 8000,
  137. .minimum_ms = 10,
  138. .maximum_ms = 150,
  139. .default_ms = 20,
  140. .minimum_bytes = 80,
  141. .samples_count = ulaw_samples,
  142. .get_length = ulaw_length,
  143. .smooth = 1,
  144. };
  145. static int gsm_samples(struct ast_frame *frame)
  146. {
  147. return 160 * (frame->datalen / 33);
  148. }
  149. static int gsm_length(unsigned int samples)
  150. {
  151. return (samples / 160) * 33;
  152. }
  153. static struct ast_codec gsm = {
  154. .name = "gsm",
  155. .description = "GSM",
  156. .type = AST_MEDIA_TYPE_AUDIO,
  157. .sample_rate = 8000,
  158. .minimum_ms = 20,
  159. .maximum_ms = 300,
  160. .default_ms = 20,
  161. .minimum_bytes = 33,
  162. .samples_count = gsm_samples,
  163. .get_length = gsm_length,
  164. .smooth = 1,
  165. };
  166. static int g726_samples(struct ast_frame *frame)
  167. {
  168. return frame->datalen * 2;
  169. }
  170. static int g726_length(unsigned int samples)
  171. {
  172. return samples / 2;
  173. }
  174. static struct ast_codec g726rfc3551 = {
  175. .name = "g726",
  176. .description = "G.726 RFC3551",
  177. .type = AST_MEDIA_TYPE_AUDIO,
  178. .sample_rate = 8000,
  179. .minimum_ms = 10,
  180. .maximum_ms = 300,
  181. .default_ms = 20,
  182. .minimum_bytes = 40,
  183. .samples_count = g726_samples,
  184. .get_length = g726_length,
  185. .smooth = 1,
  186. };
  187. static struct ast_codec g726aal2 = {
  188. .name = "g726aal2",
  189. .description = "G.726 AAL2",
  190. .type = AST_MEDIA_TYPE_AUDIO,
  191. .sample_rate = 8000,
  192. .minimum_ms = 10,
  193. .maximum_ms = 300,
  194. .default_ms = 20,
  195. .minimum_bytes = 40,
  196. .samples_count = g726_samples,
  197. .get_length = g726_length,
  198. .smooth = 1,
  199. };
  200. static struct ast_codec adpcm = {
  201. .name = "adpcm",
  202. .description = "Dialogic ADPCM",
  203. .type = AST_MEDIA_TYPE_AUDIO,
  204. .sample_rate = 8000,
  205. .minimum_ms = 10,
  206. .maximum_ms = 300,
  207. .default_ms = 20,
  208. .minimum_bytes = 40,
  209. .samples_count = g726_samples,
  210. .get_length = g726_length,
  211. .smooth = 1,
  212. };
  213. static int slin_samples(struct ast_frame *frame)
  214. {
  215. return frame->datalen / 2;
  216. }
  217. static int slin_length(unsigned int samples)
  218. {
  219. return samples * 2;
  220. }
  221. static struct ast_codec slin8 = {
  222. .name = "slin",
  223. .description = "16 bit Signed Linear PCM",
  224. .type = AST_MEDIA_TYPE_AUDIO,
  225. .sample_rate = 8000,
  226. .minimum_ms = 10,
  227. .maximum_ms = 70,
  228. .default_ms = 20,
  229. .minimum_bytes = 160,
  230. .samples_count = slin_samples,
  231. .get_length = slin_length,
  232. .smooth = 1,
  233. };
  234. static struct ast_codec slin12 = {
  235. .name = "slin",
  236. .description = "16 bit Signed Linear PCM (12kHz)",
  237. .type = AST_MEDIA_TYPE_AUDIO,
  238. .sample_rate = 12000,
  239. .minimum_ms = 10,
  240. .maximum_ms = 70,
  241. .default_ms = 20,
  242. .minimum_bytes = 240,
  243. .samples_count = slin_samples,
  244. .get_length = slin_length,
  245. .smooth = 1,
  246. };
  247. static struct ast_codec slin16 = {
  248. .name = "slin",
  249. .description = "16 bit Signed Linear PCM (16kHz)",
  250. .type = AST_MEDIA_TYPE_AUDIO,
  251. .sample_rate = 16000,
  252. .minimum_ms = 10,
  253. .maximum_ms = 70,
  254. .default_ms = 20,
  255. .minimum_bytes = 320,
  256. .samples_count = slin_samples,
  257. .get_length = slin_length,
  258. .smooth = 1,
  259. };
  260. static struct ast_codec slin24 = {
  261. .name = "slin",
  262. .description = "16 bit Signed Linear PCM (24kHz)",
  263. .type = AST_MEDIA_TYPE_AUDIO,
  264. .sample_rate = 24000,
  265. .minimum_ms = 10,
  266. .maximum_ms = 70,
  267. .default_ms = 20,
  268. .minimum_bytes = 480,
  269. .samples_count = slin_samples,
  270. .get_length = slin_length,
  271. .smooth = 1,
  272. };
  273. static struct ast_codec slin32 = {
  274. .name = "slin",
  275. .description = "16 bit Signed Linear PCM (32kHz)",
  276. .type = AST_MEDIA_TYPE_AUDIO,
  277. .sample_rate = 32000,
  278. .minimum_ms = 10,
  279. .maximum_ms = 70,
  280. .default_ms = 20,
  281. .minimum_bytes = 640,
  282. .samples_count = slin_samples,
  283. .get_length = slin_length,
  284. .smooth = 1,
  285. };
  286. static struct ast_codec slin44 = {
  287. .name = "slin",
  288. .description = "16 bit Signed Linear PCM (44kHz)",
  289. .type = AST_MEDIA_TYPE_AUDIO,
  290. .sample_rate = 44100,
  291. .minimum_ms = 10,
  292. .maximum_ms = 70,
  293. .default_ms = 20,
  294. .minimum_bytes = 882,
  295. .samples_count = slin_samples,
  296. .get_length = slin_length,
  297. .smooth = 1,
  298. };
  299. static struct ast_codec slin48 = {
  300. .name = "slin",
  301. .description = "16 bit Signed Linear PCM (48kHz)",
  302. .type = AST_MEDIA_TYPE_AUDIO,
  303. .sample_rate = 48000,
  304. .minimum_ms = 10,
  305. .maximum_ms = 70,
  306. .default_ms = 20,
  307. .minimum_bytes = 960,
  308. .samples_count = slin_samples,
  309. .get_length = slin_length,
  310. .smooth = 1,
  311. };
  312. static struct ast_codec slin96 = {
  313. .name = "slin",
  314. .description = "16 bit Signed Linear PCM (96kHz)",
  315. .type = AST_MEDIA_TYPE_AUDIO,
  316. .sample_rate = 96000,
  317. .minimum_ms = 10,
  318. .maximum_ms = 70,
  319. .default_ms = 20,
  320. .minimum_bytes = 1920,
  321. .samples_count = slin_samples,
  322. .get_length = slin_length,
  323. .smooth = 1,
  324. };
  325. static struct ast_codec slin192 = {
  326. .name = "slin",
  327. .description = "16 bit Signed Linear PCM (192kHz)",
  328. .type = AST_MEDIA_TYPE_AUDIO,
  329. .sample_rate = 192000,
  330. .minimum_ms = 10,
  331. .maximum_ms = 70,
  332. .default_ms = 20,
  333. .minimum_bytes = 3840,
  334. .samples_count = slin_samples,
  335. .get_length = slin_length,
  336. .smooth = 1,
  337. };
  338. static int lpc10_samples(struct ast_frame *frame)
  339. {
  340. int samples = 22 * 8;
  341. /* assumes that the RTP packet contains one LPC10 frame */
  342. samples += (((char *)(frame->data.ptr))[7] & 0x1) * 8;
  343. return samples;
  344. }
  345. static struct ast_codec lpc10 = {
  346. .name = "lpc10",
  347. .description = "LPC10",
  348. .type = AST_MEDIA_TYPE_AUDIO,
  349. .sample_rate = 8000,
  350. .minimum_ms = 20,
  351. .maximum_ms = 20,
  352. .default_ms = 20,
  353. .minimum_bytes = 7,
  354. .samples_count = lpc10_samples,
  355. .smooth = 1,
  356. };
  357. static int g729_samples(struct ast_frame *frame)
  358. {
  359. return frame->datalen * 8;
  360. }
  361. static int g729_length(unsigned int samples)
  362. {
  363. return samples / 8;
  364. }
  365. static struct ast_codec g729a = {
  366. .name = "g729",
  367. .description = "G.729A",
  368. .type = AST_MEDIA_TYPE_AUDIO,
  369. .sample_rate = 8000,
  370. .minimum_ms = 10,
  371. .maximum_ms = 230,
  372. .default_ms = 20,
  373. .minimum_bytes = 10,
  374. .samples_count = g729_samples,
  375. .get_length = g729_length,
  376. .smooth = 1,
  377. };
  378. static unsigned char get_n_bits_at(unsigned char *data, int n, int bit)
  379. {
  380. int byte = bit / 8; /* byte containing first bit */
  381. int rem = 8 - (bit % 8); /* remaining bits in first byte */
  382. unsigned char ret = 0;
  383. if (n <= 0 || n > 8)
  384. return 0;
  385. if (rem < n) {
  386. ret = (data[byte] << (n - rem));
  387. ret |= (data[byte + 1] >> (8 - n + rem));
  388. } else {
  389. ret = (data[byte] >> (rem - n));
  390. }
  391. return (ret & (0xff >> (8 - n)));
  392. }
  393. static int speex_get_wb_sz_at(unsigned char *data, int len, int bit)
  394. {
  395. static const int SpeexWBSubModeSz[] = {
  396. 4, 36, 112, 192,
  397. 352, 0, 0, 0 };
  398. int off = bit;
  399. unsigned char c;
  400. /* skip up to two wideband frames */
  401. if (((len * 8 - off) >= 5) &&
  402. get_n_bits_at(data, 1, off)) {
  403. c = get_n_bits_at(data, 3, off + 1);
  404. off += SpeexWBSubModeSz[c];
  405. if (((len * 8 - off) >= 5) &&
  406. get_n_bits_at(data, 1, off)) {
  407. c = get_n_bits_at(data, 3, off + 1);
  408. off += SpeexWBSubModeSz[c];
  409. if (((len * 8 - off) >= 5) &&
  410. get_n_bits_at(data, 1, off)) {
  411. ast_log(LOG_WARNING, "Encountered corrupt speex frame; too many wideband frames in a row.\n");
  412. return -1;
  413. }
  414. }
  415. }
  416. return off - bit;
  417. }
  418. static int speex_samples(unsigned char *data, int len)
  419. {
  420. static const int SpeexSubModeSz[] = {
  421. 5, 43, 119, 160,
  422. 220, 300, 364, 492,
  423. 79, 0, 0, 0,
  424. 0, 0, 0, 0 };
  425. static const int SpeexInBandSz[] = {
  426. 1, 1, 4, 4,
  427. 4, 4, 4, 4,
  428. 8, 8, 16, 16,
  429. 32, 32, 64, 64 };
  430. int bit = 0;
  431. int cnt = 0;
  432. int off;
  433. unsigned char c;
  434. while ((len * 8 - bit) >= 5) {
  435. /* skip wideband frames */
  436. off = speex_get_wb_sz_at(data, len, bit);
  437. if (off < 0) {
  438. ast_log(LOG_WARNING, "Had error while reading wideband frames for speex samples\n");
  439. break;
  440. }
  441. bit += off;
  442. if ((len * 8 - bit) < 5)
  443. break;
  444. /* get control bits */
  445. c = get_n_bits_at(data, 5, bit);
  446. bit += 5;
  447. if (c == 15) {
  448. /* terminator */
  449. break;
  450. } else if (c == 14) {
  451. /* in-band signal; next 4 bits contain signal id */
  452. c = get_n_bits_at(data, 4, bit);
  453. bit += 4;
  454. bit += SpeexInBandSz[c];
  455. } else if (c == 13) {
  456. /* user in-band; next 4 bits contain msg len */
  457. c = get_n_bits_at(data, 4, bit);
  458. bit += 4;
  459. /* after which it's 5-bit signal id + c bytes of data */
  460. bit += 5 + c * 8;
  461. } else if (c > 8) {
  462. /* unknown */
  463. ast_log(LOG_WARNING, "Unknown speex control frame %d\n", c);
  464. break;
  465. } else {
  466. /* skip number bits for submode (less the 5 control bits) */
  467. bit += SpeexSubModeSz[c] - 5;
  468. cnt += 160; /* new frame */
  469. }
  470. }
  471. return cnt;
  472. }
  473. static int speex8_samples(struct ast_frame *frame)
  474. {
  475. return speex_samples(frame->data.ptr, frame->datalen);
  476. }
  477. static struct ast_codec speex8 = {
  478. .name = "speex",
  479. .description = "SpeeX",
  480. .type = AST_MEDIA_TYPE_AUDIO,
  481. .sample_rate = 8000,
  482. .minimum_ms = 10,
  483. .maximum_ms = 60,
  484. .default_ms = 20,
  485. .minimum_bytes = 10,
  486. .samples_count = speex8_samples,
  487. };
  488. static int speex16_samples(struct ast_frame *frame)
  489. {
  490. return 2 * speex_samples(frame->data.ptr, frame->datalen);
  491. }
  492. static struct ast_codec speex16 = {
  493. .name = "speex",
  494. .description = "SpeeX 16khz",
  495. .type = AST_MEDIA_TYPE_AUDIO,
  496. .sample_rate = 16000,
  497. .minimum_ms = 10,
  498. .maximum_ms = 60,
  499. .default_ms = 20,
  500. .minimum_bytes = 10,
  501. .samples_count = speex16_samples,
  502. };
  503. static int speex32_samples(struct ast_frame *frame)
  504. {
  505. return 4 * speex_samples(frame->data.ptr, frame->datalen);
  506. }
  507. static struct ast_codec speex32 = {
  508. .name = "speex",
  509. .description = "SpeeX 32khz",
  510. .type = AST_MEDIA_TYPE_AUDIO,
  511. .sample_rate = 32000,
  512. .minimum_ms = 10,
  513. .maximum_ms = 60,
  514. .default_ms = 20,
  515. .minimum_bytes = 10,
  516. .samples_count = speex32_samples,
  517. };
  518. static int ilbc_samples(struct ast_frame *frame)
  519. {
  520. return 240 * (frame->datalen / 50);
  521. }
  522. static struct ast_codec ilbc = {
  523. .name = "ilbc",
  524. .description = "iLBC",
  525. .type = AST_MEDIA_TYPE_AUDIO,
  526. .sample_rate = 8000,
  527. .minimum_ms = 30,
  528. .maximum_ms = 30,
  529. .default_ms = 30,
  530. .minimum_bytes = 50,
  531. .samples_count = ilbc_samples,
  532. .smooth = 1,
  533. };
  534. static struct ast_codec g722 = {
  535. .name = "g722",
  536. .description = "G722",
  537. .type = AST_MEDIA_TYPE_AUDIO,
  538. .sample_rate = 16000,
  539. .minimum_ms = 10,
  540. .maximum_ms = 150,
  541. .default_ms = 20,
  542. .minimum_bytes = 80,
  543. .samples_count = g726_samples,
  544. .get_length = g726_length,
  545. .smooth = 1,
  546. };
  547. static int siren7_samples(struct ast_frame *frame)
  548. {
  549. return frame->datalen * (16000 / 4000);
  550. }
  551. static int siren7_length(unsigned int samples)
  552. {
  553. return samples / (16000 / 4000);
  554. }
  555. static struct ast_codec siren7 = {
  556. .name = "siren7",
  557. .description = "ITU G.722.1 (Siren7, licensed from Polycom)",
  558. .type = AST_MEDIA_TYPE_AUDIO,
  559. .sample_rate = 16000,
  560. .minimum_ms = 20,
  561. .maximum_ms = 80,
  562. .default_ms = 20,
  563. .minimum_bytes = 80,
  564. .samples_count = siren7_samples,
  565. .get_length = siren7_length,
  566. };
  567. static int siren14_samples(struct ast_frame *frame)
  568. {
  569. return (int) frame->datalen * ((float) 32000 / 6000);
  570. }
  571. static int siren14_length(unsigned int samples)
  572. {
  573. return (int) samples / ((float) 32000 / 6000);;
  574. }
  575. static struct ast_codec siren14 = {
  576. .name = "siren14",
  577. .description = "ITU G.722.1 Annex C, (Siren14, licensed from Polycom)",
  578. .type = AST_MEDIA_TYPE_AUDIO,
  579. .sample_rate = 32000,
  580. .minimum_ms = 20,
  581. .maximum_ms = 80,
  582. .default_ms = 20,
  583. .minimum_bytes = 120,
  584. .samples_count = siren14_samples,
  585. .get_length = siren14_length,
  586. };
  587. static struct ast_codec testlaw = {
  588. .name = "testlaw",
  589. .description = "G.711 test-law",
  590. .type = AST_MEDIA_TYPE_AUDIO,
  591. .sample_rate = 8000,
  592. .minimum_ms = 10,
  593. .maximum_ms = 150,
  594. .default_ms = 20,
  595. .minimum_bytes = 80,
  596. .samples_count = ulaw_samples,
  597. .get_length = ulaw_length,
  598. .smooth = 1,
  599. };
  600. static int g719_samples(struct ast_frame *frame)
  601. {
  602. return (int) frame->datalen * ((float) 48000 / 8000);
  603. }
  604. static int g719_length(unsigned int samples)
  605. {
  606. return (int) samples / ((float) 48000 / 8000);
  607. }
  608. static struct ast_codec g719 = {
  609. .name = "g719",
  610. .description = "ITU G.719",
  611. .type = AST_MEDIA_TYPE_AUDIO,
  612. .sample_rate = 48000,
  613. .minimum_ms = 20,
  614. .maximum_ms = 80,
  615. .default_ms = 20,
  616. .minimum_bytes = 160,
  617. .samples_count = g719_samples,
  618. .get_length = g719_length,
  619. };
  620. static struct ast_codec opus = {
  621. .name = "opus",
  622. .description = "Opus Codec",
  623. .type = AST_MEDIA_TYPE_AUDIO,
  624. .sample_rate = 48000,
  625. .minimum_ms = 20,
  626. .maximum_ms = 60,
  627. .default_ms = 20,
  628. .minimum_bytes = 10,
  629. };
  630. static struct ast_codec jpeg = {
  631. .name = "jpeg",
  632. .description = "JPEG image",
  633. .type = AST_MEDIA_TYPE_IMAGE,
  634. };
  635. static struct ast_codec png = {
  636. .name = "png",
  637. .description = "PNG Image",
  638. .type = AST_MEDIA_TYPE_IMAGE,
  639. };
  640. static struct ast_codec h261 = {
  641. .name = "h261",
  642. .description = "H.261 video",
  643. .type = AST_MEDIA_TYPE_VIDEO,
  644. };
  645. static struct ast_codec h263 = {
  646. .name = "h263",
  647. .description = "H.263 video",
  648. .type = AST_MEDIA_TYPE_VIDEO,
  649. };
  650. static struct ast_codec h263p = {
  651. .name = "h263p",
  652. .description = "H.263+ video",
  653. .type = AST_MEDIA_TYPE_VIDEO,
  654. };
  655. static struct ast_codec h264 = {
  656. .name = "h264",
  657. .description = "H.264 video",
  658. .type = AST_MEDIA_TYPE_VIDEO,
  659. };
  660. static struct ast_codec mpeg4 = {
  661. .name = "mpeg4",
  662. .description = "MPEG4 video",
  663. .type = AST_MEDIA_TYPE_VIDEO,
  664. };
  665. static struct ast_codec vp8 = {
  666. .name = "vp8",
  667. .description = "VP8 video",
  668. .type = AST_MEDIA_TYPE_VIDEO,
  669. };
  670. static struct ast_codec t140red = {
  671. .name = "red",
  672. .description = "T.140 Realtime Text with redundancy",
  673. .type = AST_MEDIA_TYPE_TEXT,
  674. };
  675. static struct ast_codec t140 = {
  676. .name = "t140",
  677. .description = "Passthrough T.140 Realtime Text",
  678. .type = AST_MEDIA_TYPE_TEXT,
  679. };
  680. #define CODEC_REGISTER_AND_CACHE(codec) \
  681. ({ \
  682. int __res_ ## __LINE__ = 0; \
  683. struct ast_format *__fmt_ ## __LINE__; \
  684. struct ast_codec *__codec_ ## __LINE__; \
  685. res |= __ast_codec_register(&(codec), NULL); \
  686. __codec_ ## __LINE__ = ast_codec_get((codec).name, (codec).type, (codec).sample_rate); \
  687. __fmt_ ## __LINE__ = ast_format_create(__codec_ ## __LINE__); \
  688. res |= ast_format_cache_set(__fmt_ ## __LINE__); \
  689. ao2_ref(__fmt_ ## __LINE__, -1); \
  690. ao2_ref(__codec_ ## __LINE__, -1); \
  691. __res_ ## __LINE__; \
  692. })
  693. #define CODEC_REGISTER_AND_CACHE_NAMED(format_name, codec) \
  694. ({ \
  695. int __res_ ## __LINE__ = 0; \
  696. struct ast_format *__fmt_ ## __LINE__; \
  697. struct ast_codec *__codec_ ## __LINE__; \
  698. res |= __ast_codec_register(&(codec), NULL); \
  699. __codec_ ## __LINE__ = ast_codec_get((codec).name, (codec).type, (codec).sample_rate); \
  700. __fmt_ ## __LINE__ = ast_format_create_named((format_name), __codec_ ## __LINE__); \
  701. res |= ast_format_cache_set(__fmt_ ## __LINE__); \
  702. ao2_ref(__fmt_ ## __LINE__, -1); \
  703. ao2_ref(__codec_ ## __LINE__, -1); \
  704. __res_ ## __LINE__; \
  705. })
  706. int ast_codec_builtin_init(void)
  707. {
  708. int res = 0;
  709. res |= CODEC_REGISTER_AND_CACHE(g723);
  710. res |= CODEC_REGISTER_AND_CACHE(ulaw);
  711. res |= CODEC_REGISTER_AND_CACHE(alaw);
  712. res |= CODEC_REGISTER_AND_CACHE(gsm);
  713. res |= CODEC_REGISTER_AND_CACHE(g726rfc3551);
  714. res |= CODEC_REGISTER_AND_CACHE(g726aal2);
  715. res |= CODEC_REGISTER_AND_CACHE(adpcm);
  716. res |= CODEC_REGISTER_AND_CACHE(slin8);
  717. res |= CODEC_REGISTER_AND_CACHE_NAMED("slin12", slin12);
  718. res |= CODEC_REGISTER_AND_CACHE_NAMED("slin16", slin16);
  719. res |= CODEC_REGISTER_AND_CACHE_NAMED("slin24", slin24);
  720. res |= CODEC_REGISTER_AND_CACHE_NAMED("slin32", slin32);
  721. res |= CODEC_REGISTER_AND_CACHE_NAMED("slin44", slin44);
  722. res |= CODEC_REGISTER_AND_CACHE_NAMED("slin48", slin48);
  723. res |= CODEC_REGISTER_AND_CACHE_NAMED("slin96", slin96);
  724. res |= CODEC_REGISTER_AND_CACHE_NAMED("slin192", slin192);
  725. res |= CODEC_REGISTER_AND_CACHE(lpc10);
  726. res |= CODEC_REGISTER_AND_CACHE(g729a);
  727. res |= CODEC_REGISTER_AND_CACHE(speex8);
  728. res |= CODEC_REGISTER_AND_CACHE_NAMED("speex16", speex16);
  729. res |= CODEC_REGISTER_AND_CACHE_NAMED("speex32", speex32);
  730. res |= CODEC_REGISTER_AND_CACHE(ilbc);
  731. res |= CODEC_REGISTER_AND_CACHE(g722);
  732. res |= CODEC_REGISTER_AND_CACHE(siren7);
  733. res |= CODEC_REGISTER_AND_CACHE(siren14);
  734. res |= CODEC_REGISTER_AND_CACHE(testlaw);
  735. res |= CODEC_REGISTER_AND_CACHE(g719);
  736. res |= CODEC_REGISTER_AND_CACHE(opus);
  737. res |= CODEC_REGISTER_AND_CACHE(jpeg);
  738. res |= CODEC_REGISTER_AND_CACHE(png);
  739. res |= CODEC_REGISTER_AND_CACHE(h261);
  740. res |= CODEC_REGISTER_AND_CACHE(h263);
  741. res |= CODEC_REGISTER_AND_CACHE(h263p);
  742. res |= CODEC_REGISTER_AND_CACHE(h264);
  743. res |= CODEC_REGISTER_AND_CACHE(mpeg4);
  744. res |= CODEC_REGISTER_AND_CACHE(vp8);
  745. res |= CODEC_REGISTER_AND_CACHE(t140red);
  746. res |= CODEC_REGISTER_AND_CACHE(t140);
  747. res |= CODEC_REGISTER_AND_CACHE(none);
  748. return res;
  749. }