diff options
Diffstat (limited to 'apps')
-rw-r--r-- | apps/codecs/libwma/SOURCES | 1 | ||||
-rw-r--r-- | apps/codecs/libwma/wmadata.h | 108 | ||||
-rw-r--r-- | apps/codecs/libwma/wmadeci.c | 521 | ||||
-rw-r--r-- | apps/codecs/libwma/wmafixed.c | 350 | ||||
-rw-r--r-- | apps/codecs/libwma/wmafixed.h | 92 |
5 files changed, 551 insertions, 521 deletions
diff --git a/apps/codecs/libwma/SOURCES b/apps/codecs/libwma/SOURCES index 3351bb27b8..190e3a7ba3 100644 --- a/apps/codecs/libwma/SOURCES +++ b/apps/codecs/libwma/SOURCES | |||
@@ -1,2 +1,3 @@ | |||
1 | wmadeci.c | 1 | wmadeci.c |
2 | common.c | 2 | common.c |
3 | wmafixed.c \ No newline at end of file | ||
diff --git a/apps/codecs/libwma/wmadata.h b/apps/codecs/libwma/wmadata.h index ee17207102..ae4844e152 100644 --- a/apps/codecs/libwma/wmadata.h +++ b/apps/codecs/libwma/wmadata.h | |||
@@ -1389,24 +1389,118 @@ static const uint16_t levels5[40] = { | |||
1389 | 1, 1, 1, 1, 1, 1, 1, 1, | 1389 | 1, 1, 1, 1, 1, 1, 1, 1, |
1390 | 1, 1, 1, 1, 1, 1, 1, 1, | 1390 | 1, 1, 1, 1, 1, 1, 1, 1, |
1391 | }; | 1391 | }; |
1392 | 1392 | ||
1393 | static const CoefVLCTable coef_vlcs[6] = { | 1393 | static const CoefVLCTable coef_vlcs[6] = { |
1394 | { | 1394 | { |
1395 | sizeof(coef0_huffbits), coef0_huffcodes, coef0_huffbits, levels0, | 1395 | sizeof(coef0_huffbits), coef0_huffcodes, coef0_huffbits, levels0, |
1396 | }, | 1396 | }, |
1397 | { | 1397 | { |
1398 | sizeof(coef1_huffbits), coef1_huffcodes, coef1_huffbits, levels1, | 1398 | sizeof(coef1_huffbits), coef1_huffcodes, coef1_huffbits, levels1, |
1399 | }, | 1399 | }, |
1400 | { | 1400 | { |
1401 | sizeof(coef2_huffbits), coef2_huffcodes, coef2_huffbits, levels2, | 1401 | sizeof(coef2_huffbits), coef2_huffcodes, coef2_huffbits, levels2, |
1402 | }, | 1402 | }, |
1403 | { | 1403 | { |
1404 | sizeof(coef3_huffbits), coef3_huffcodes, coef3_huffbits, levels3, | 1404 | sizeof(coef3_huffbits), coef3_huffcodes, coef3_huffbits, levels3, |
1405 | }, | 1405 | }, |
1406 | { | 1406 | { |
1407 | sizeof(coef4_huffbits), coef4_huffcodes, coef4_huffbits, levels4, | 1407 | sizeof(coef4_huffbits), coef4_huffcodes, coef4_huffbits, levels4, |
1408 | }, | 1408 | }, |
1409 | { | 1409 | { |
1410 | sizeof(coef5_huffbits), coef5_huffcodes, coef5_huffbits, levels5, | 1410 | sizeof(coef5_huffbits), coef5_huffcodes, coef5_huffbits, levels5, |
1411 | }, | 1411 | }, |
1412 | }; | 1412 | }; |
1413 | |||
1414 | |||
1415 | const fixed64 pow_table[] = | ||
1416 | { | ||
1417 | 0x10000LL,0x11f3dLL,0x14249LL,0x1699cLL,0x195bcLL,0x1c73dLL,0x1fec9LL,0x23d1dLL,0x2830bLL,0x2d182LL, | ||
1418 | 0x3298bLL,0x38c53LL,0x3fb28LL,0x47783LL,0x5030aLL,0x59f98LL,0x64f40LL,0x71457LL,0x7f17bLL,0x8e99aLL, | ||
1419 | 0xa0000LL,0xb385eLL,0xc96d9LL,0xe2019LL,0xfd954LL,0x11c865LL,0x13f3dfLL,0x166320LL,0x191e6eLL,0x1c2f10LL, | ||
1420 | 0x1f9f6eLL,0x237b39LL,0x27cf8bLL,0x2cab1aLL,0x321e65LL,0x383bf0LL,0x3f1882LL,0x46cb6aLL,0x4f6eceLL,0x592006LL, | ||
1421 | 0x640000LL,0x7033acLL,0x7de47eLL,0x8d40f6LL,0x9e7d44LL,0xb1d3f4LL,0xc786b7LL,0xdfdf43LL,0xfb304bLL,0x119d69aLL, | ||
1422 | 0x13c3a4eLL,0x162d03aLL,0x18e1b70LL,0x1beaf00LL,0x1f52feeLL,0x2325760LL,0x276f514LL,0x2c3f220LL,0x31a5408LL, | ||
1423 | 0x37b403cLL,0x3e80000LL,0x46204b8LL,0x4eaece8LL,0x58489a0LL,0x630e4a8LL,0x6f24788LL,0x7cb4328LL,0x8beb8a0LL, | ||
1424 | 0x9cfe2f0LL,0xb026200LL,0xc5a4710LL,0xddc2240LL,0xf8d1260LL,0x1172d600LL,0x1393df60LL,0x15f769c0LL,0x18a592c0LL, | ||
1425 | 0x1ba77540LL,0x1f074840LL,0x22d08280LL,0x27100000LL,0x2bd42f40LL,0x312d4100LL,0x372d6000LL,0x3de8ee80LL, | ||
1426 | 0x4576cb80LL,0x4df09f80LL,0x57733600LL,0x621edd80LL,0x6e17d480LL,0x7b86c700LL,0x8a995700LL,0x9b82b800LL, | ||
1427 | 0xae7c5c00LL,0xc3c6b900LL,0xdbaa2200LL,0xf677bc00LL,0x1148a9400LL,0x13648d200LL,0x15c251800LL,0x186a00000LL, | ||
1428 | 0x1b649d800LL,0x1ebc48a00LL,0x227c5c000LL,0x26b195000LL,0x2b6a3f000LL,0x30b663c00LL,0x36a801c00LL,0x3d534a400LL, | ||
1429 | 0x44cee4800LL,0x4d343c800LL,0x569fd6000LL,0x6131b2800LL,0x6d0db9800LL,0x7a5c33800LL,0x894a55000LL,0x9a0ad6000LL, | ||
1430 | 0xacd69d000LL,0xc1ed84000LL,0xd9972f000LL,0xf42400000LL,0x111ee28000LL,0x1335ad6000LL,0x158db98000LL,0x182efd4000LL, | ||
1431 | 0x1b22676000LL,0x1e71fe6000LL,0x2229014000LL,0x26540e8000LL,0x2b014f0000LL,0x3040a5c000LL,0x3623e60000LL,0x3cbf0fc000LL, | ||
1432 | 0x4428940000LL,0x4c79a08000LL,0x55ce758000LL,0x6046c58000LL,0x6c06220000LL,0x7934728000LL,0x87fe7d0000LL,0x9896800000LL, | ||
1433 | 0xab34d90000LL,0xc018c60000LL,0xd7893f0000LL,0xf1d5e40000LL,0x10f580a0000LL,0x13073f00000LL,0x1559a0c0000LL,0x17f48900000LL, | ||
1434 | 0x1ae0d160000LL,0x1e286780000LL,0x21d66fc0000LL,0x25f769c0000LL,0x2a995c80000LL,0x2fcc0440000LL,0x35a10940000LL, | ||
1435 | 0x3c2c3b80000LL,0x4383d500000LL,0x4bc0c780000LL,0x54ff0e80000LL,0x5f5e1000000LL,0x6b010780000LL,0x780f7c00000LL, | ||
1436 | 0x86b5c800000LL,0x9725ae00000LL,0xa9970600000LL,0xbe487500000LL,0xd5804700000LL,0xef8d5a00000LL,0x10cc82e00000LL, | ||
1437 | 0x12d940c00000LL,0x152605c00000LL,0x17baa2200000LL,0x1a9fd9c00000LL,0x1ddf82a00000LL,0x2184a5c00000LL,0x259ba5400000LL, | ||
1438 | 0x2a3265400000LL,0x2f587cc00000LL,0x351f69000000LL,0x3b9aca000000LL,0x42e0a4800000LL,0x4b09ad800000LL, | ||
1439 | 0x54319d000000LL,0x5e778d000000LL,0x69fe64000000LL,0x76ed49800000LL,0x85702c000000LL,0x95b858000000LL, | ||
1440 | 0xa7fd1c000000LL,0xbc7c87000000LL,0xd37c3a000000LL,0xed4a55000000LL,0x10a3e82000000LL,0x12abb1a000000LL, | ||
1441 | 0x14f2e7a000000LL,0x1781474000000LL,0x1a5f7f4000000LL,0x1d974de000000LL,0x2133a18000000LL | ||
1442 | }; | ||
1443 | |||
1444 | const fixed32 pow_10_to_yover16[] ICONST_ATTR= | ||
1445 | { | ||
1446 | 0x10000,0x127a0,0x15562,0x18a39,0x1c73d,0x20db4,0x25f12,0x2bd09,0x3298b,0x3a6d9,0x4378b,0x4dea3, | ||
1447 | 0x59f98,0x67e6b,0x77fbb,0x8a8de,0xa0000,0xb8c3e,0xd55d1,0xf6636,0x11c865,0x148906,0x17b6b8,0x1b625b, | ||
1448 | 0x1f9f6e,0x248475,0x2a2b6e,0x30b25f,0x383bf0,0x40f02c,0x4afd4b,0x5698b0,0x640000,0x737a6b,0x855a26, | ||
1449 | 0x99fe1f,0xb1d3f4,0xcd5a3e,0xed232b,0x111d78a,0x13c3a4e,0x16d2c94,0x1a5b24e,0x1e6f7b0,0x2325760, | ||
1450 | 0x28961b4,0x2ede4ec,0x361f6dc,0x3e80000,0x482c830,0x5358580,0x603ed30,0x6f24788,0x8058670,0x9435fb0, | ||
1451 | 0xab26b70,0xc5a4710,0xe43bdc0,0x1078f700,0x1305ace0,0x15f769c0,0x195dd100,0x1d4af120 | ||
1452 | }; | ||
1453 | |||
1454 | const fixed32 pow_a_table[] = | ||
1455 | { | ||
1456 | 0x1004,0x1008,0x100c,0x1010,0x1014,0x1018,0x101c,0x1021,0x1025,0x1029,0x102d,0x1031,0x1036,0x103a, | ||
1457 | 0x103e,0x1043,0x1047,0x104b,0x1050,0x1054,0x1059,0x105d,0x1062,0x1066,0x106b,0x106f,0x1074,0x1078, | ||
1458 | 0x107d,0x1082,0x1086,0x108b,0x1090,0x1095,0x1099,0x109e,0x10a3,0x10a8,0x10ad,0x10b2,0x10b7,0x10bc, | ||
1459 | 0x10c1,0x10c6,0x10cb,0x10d0,0x10d5,0x10da,0x10df,0x10e5,0x10ea,0x10ef,0x10f5,0x10fa,0x10ff,0x1105, | ||
1460 | 0x110a,0x1110,0x1115,0x111b,0x1120,0x1126,0x112c,0x1131,0x1137,0x113d,0x1143,0x1149,0x114f,0x1155, | ||
1461 | 0x115a,0x1161,0x1167,0x116d,0x1173,0x1179,0x117f,0x1186,0x118c,0x1192,0x1199,0x119f,0x11a6,0x11ac, | ||
1462 | 0x11b3,0x11b9,0x11c0,0x11c7,0x11ce,0x11d4,0x11db,0x11e2,0x11e9,0x11f0,0x11f8,0x11ff,0x1206,0x120d, | ||
1463 | 0x1215,0x121c,0x1223,0x122b,0x1233,0x123a,0x1242,0x124a,0x1251,0x1259,0x1261,0x1269,0x1271,0x127a, | ||
1464 | 0x1282,0x128a,0x1293,0x129b,0x12a4,0x12ac,0x12b5,0x12be,0x12c7,0x12d0,0x12d9,0x12e2,0x12eb,0x12f4, | ||
1465 | 0x12fe,0x1307 | ||
1466 | }; | ||
1467 | |||
1468 | const fixed64 lsp_pow_e_table[] = | ||
1469 | { | ||
1470 | 0xf333f9deLL, 0xf0518db9LL, 0x0LL, 0x7e656b4fLL, 0x7999fcefLL, 0xf828c6dcLL, 0x0LL, | ||
1471 | 0x3f32b5a7LL, 0x3cccfe78LL, 0xfc14636eLL, 0x0LL, 0x9f995ad4LL, 0x9e667f3cLL, 0xfe0a31b7LL, | ||
1472 | 0x0LL, 0x4fccad6aLL, 0x4f333f9eLL, 0x7f0518dcLL, 0x0LL, 0x27e656b5LL, 0x27999fcfLL, | ||
1473 | 0xbf828c6eLL, 0x0LL, 0x13f32b5aLL, 0x13cccfe7LL, 0xdfc14637LL, 0x0LL, 0x89f995adLL, | ||
1474 | 0x9e667f4LL, 0x6fe0a31bLL, 0x0LL, 0x44fccad7LL, 0x4f333faLL, 0x37f0518eLL, 0x0LL, | ||
1475 | 0xa27e656bLL, 0x827999fdLL, 0x1bf828c7LL, 0x0LL, 0xd13f32b6LL, 0x413cccfeLL, 0xdfc1463LL, | ||
1476 | 0x0LL, 0xe89f995bLL, 0xa09e667fLL, 0x6fe0a32LL, 0x0LL, 0x744fccadLL, 0x504f3340LL, | ||
1477 | 0x837f0519LL, 0x0LL, 0xba27e657LL, 0xa82799a0LL, 0xc1bf828cLL, 0x0LL, 0x5d13f32bLL, | ||
1478 | 0xd413ccd0LL, 0x60dfc146LL, 0x0LL, 0xae89f996LL, 0x6a09e668LL, 0x306fe0a3LL, 0x0LL, | ||
1479 | 0xd744fccbLL, 0xb504f334LL, 0x9837f052LL, 0x80000000LL, 0x6ba27e65LL, 0x5a82799aLL, | ||
1480 | 0x4c1bf829LL, 0x40000000LL, 0x35d13f33LL, 0x2d413ccdLL, 0x260dfc14LL, 0x20000000LL, | ||
1481 | 0x1ae89f99LL, 0x16a09e66LL, 0x1306fe0aLL, 0x10000000LL, 0xd744fcdLL, 0xb504f33LL, | ||
1482 | 0x9837f05LL, 0x8000000LL, 0x6ba27e6LL, 0x5a8279aLL, 0x4c1bf83LL, 0x4000000LL, | ||
1483 | 0x35d13f3LL, 0x2d413cdLL, 0x260dfc1LL, 0x2000000LL, 0x1ae89faLL, 0x16a09e6LL, | ||
1484 | 0x1306fe1LL, 0x1000000LL, 0xd744fdLL, 0xb504f3LL, 0x9837f0LL, 0x800000LL, | ||
1485 | 0x6ba27eLL, 0x5a827aLL, 0x4c1bf8LL, 0x400000LL, 0x35d13fLL, 0x2d413dLL, | ||
1486 | 0x260dfcLL, 0x200000LL, 0x1ae8a0LL, 0x16a09eLL, 0x1306feLL, 0x100000LL, | ||
1487 | 0xd7450LL, 0xb504fLL, 0x9837fLL, 0x80000LL, 0x6ba28LL, 0x5a828LL, 0x4c1c0LL, | ||
1488 | 0x40000LL, 0x35d14LL, 0x2d414LL, 0x260e0LL, 0x20000LL, 0x1ae8aLL, 0x16a0aLL, | ||
1489 | 0x13070LL, 0x10000LL, 0xd745LL, 0xb505LL, 0x9838LL, 0x8000LL, 0x6ba2LL, | ||
1490 | 0x5a82LL, 0x4c1cLL, 0x4000LL, 0x35d1LL, 0x2d41LL, 0x260eLL, 0x2000LL, | ||
1491 | 0x1ae9LL, 0x16a1LL, 0x1307LL, 0x1000LL, 0xd74LL, 0xb50LL, 0x983LL, 0x800LL, | ||
1492 | 0x6baLL, 0x5a8LL, 0x4c2LL, 0x400LL, 0x35dLL, 0x2d4LL, 0x261LL, 0x200LL, 0x1afLL, | ||
1493 | 0x16aLL, 0x130LL, 0x100LL, 0xd7LL, 0xb5LL, 0x98LL, 0x80LL, 0x6cLL, 0x5bLL, | ||
1494 | 0x4cLL, 0x40LL, 0x36LL, 0x2dLL, 0x26LL, 0x20LL, 0x1bLL, 0x17LL, 0x13LL, | ||
1495 | 0x10LL, 0xdLL, 0xbLL, 0xaLL, 0x8LL, 0x7LL, 0x6LL, 0x5LL, 0x4LL, 0x3LL, | ||
1496 | 0x3LL, 0x2LL, 0x2LL, 0x2LL, 0x1LL, 0x1LL, 0x1LL, 0x1LL, 0x1LL, 0x1LL, | ||
1497 | 0x1LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, | ||
1498 | 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, | ||
1499 | 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, | ||
1500 | 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, | ||
1501 | 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, | ||
1502 | 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, | ||
1503 | 0x0LL, 0x0LL | ||
1504 | }; | ||
1505 | |||
1506 | |||
diff --git a/apps/codecs/libwma/wmadeci.c b/apps/codecs/libwma/wmadeci.c index c064bf0e04..6647ed4b40 100644 --- a/apps/codecs/libwma/wmadeci.c +++ b/apps/codecs/libwma/wmadeci.c | |||
@@ -26,409 +26,9 @@ | |||
26 | #include <codecs/lib/codeclib.h> | 26 | #include <codecs/lib/codeclib.h> |
27 | #include "asf.h" | 27 | #include "asf.h" |
28 | #include "wmadec.h" | 28 | #include "wmadec.h" |
29 | #include "wmafixed.c" | ||
29 | 30 | ||
30 | /* These are for development and debugging and should not be changed unless | ||
31 | you REALLY know what you are doing ;) */ | ||
32 | //#define IGNORE_OVERFLOW | ||
33 | #define FAST_FILTERS | ||
34 | #define PRECISION 16 | ||
35 | #define PRECISION64 16 | ||
36 | 31 | ||
37 | static fixed64 IntTo64(int x) | ||
38 | { | ||
39 | fixed64 res = 0; | ||
40 | unsigned char *p = (unsigned char *)&res; | ||
41 | |||
42 | #ifdef ROCKBOX_BIG_ENDIAN | ||
43 | p[5] = x & 0xff; | ||
44 | p[4] = (x & 0xff00)>>8; | ||
45 | p[3] = (x & 0xff0000)>>16; | ||
46 | p[2] = (x & 0xff000000)>>24; | ||
47 | #else | ||
48 | p[2] = x & 0xff; | ||
49 | p[3] = (x & 0xff00)>>8; | ||
50 | p[4] = (x & 0xff0000)>>16; | ||
51 | p[5] = (x & 0xff000000)>>24; | ||
52 | #endif | ||
53 | return res; | ||
54 | } | ||
55 | |||
56 | static int IntFrom64(fixed64 x) | ||
57 | { | ||
58 | int res = 0; | ||
59 | unsigned char *p = (unsigned char *)&x; | ||
60 | |||
61 | #ifdef ROCKBOX_BIG_ENDIAN | ||
62 | res = p[5] | (p[4]<<8) | (p[3]<<16) | (p[2]<<24); | ||
63 | #else | ||
64 | res = p[2] | (p[3]<<8) | (p[4]<<16) | (p[5]<<24); | ||
65 | #endif | ||
66 | return res; | ||
67 | } | ||
68 | |||
69 | static fixed32 Fixed32From64(fixed64 x) | ||
70 | { | ||
71 | return x & 0xFFFFFFFF; | ||
72 | } | ||
73 | |||
74 | static fixed64 Fixed32To64(fixed32 x) | ||
75 | { | ||
76 | return (fixed64)x; | ||
77 | } | ||
78 | #define fixtof64(x) (float)((float)(x) / (float)(1 << PRECISION64)) //does not work on int64_t! | ||
79 | #define ftofix32(x) ((fixed32)((x) * (float)(1 << PRECISION) + ((x) < 0 ? -0.5 : 0.5))) | ||
80 | #define itofix64(x) (IntTo64(x)) | ||
81 | #define itofix32(x) ((x) << PRECISION) | ||
82 | #define fixtoi32(x) ((x) >> PRECISION) | ||
83 | #define fixtoi64(x) (IntFrom64(x)) | ||
84 | |||
85 | #ifdef CPU_ARM | ||
86 | #define fixmul32(x, y) \ | ||
87 | ({ int32_t __hi; \ | ||
88 | uint32_t __lo; \ | ||
89 | int32_t __result; \ | ||
90 | asm ("smull %0, %1, %3, %4\n\t" \ | ||
91 | "movs %0, %0, lsr %5\n\t" \ | ||
92 | "adc %2, %0, %1, lsl %6" \ | ||
93 | : "=&r" (__lo), "=&r" (__hi), "=r" (__result) \ | ||
94 | : "%r" (x), "r" (y), \ | ||
95 | "M" (PRECISION), "M" (32 - PRECISION) \ | ||
96 | : "cc"); \ | ||
97 | __result; \ | ||
98 | }) | ||
99 | #elif defined(CPU_COLDFIRE) | ||
100 | static inline int32_t fixmul32(int32_t x, int32_t y) | ||
101 | { | ||
102 | #if PRECISION != 16 | ||
103 | #warning Coldfire fixmul32() only works for PRECISION == 16 | ||
104 | #endif | ||
105 | int32_t t1; | ||
106 | asm ( | ||
107 | "mac.l %[x], %[y], %%acc0 \n" /* multiply */ | ||
108 | "mulu.l %[y], %[x] \n" /* get lower half, avoid emac stall */ | ||
109 | "movclr.l %%acc0, %[t1] \n" /* get higher half */ | ||
110 | "lsr.l #1, %[t1] \n" | ||
111 | "move.w %[t1], %[x] \n" | ||
112 | "swap %[x] \n" | ||
113 | : /* outputs */ | ||
114 | [t1]"=&d"(t1), | ||
115 | [x] "+d" (x) | ||
116 | : /* inputs */ | ||
117 | [y] "d" (y) | ||
118 | ); | ||
119 | return x; | ||
120 | } | ||
121 | #else | ||
122 | fixed32 fixmul32(fixed32 x, fixed32 y) | ||
123 | { | ||
124 | fixed64 temp; | ||
125 | float lol; | ||
126 | // int filehandle = rb->open("/mul.txt", O_WRONLY|O_CREAT|O_APPEND); | ||
127 | lol= fixtof64(x) * fixtof64(y); | ||
128 | |||
129 | temp = x; | ||
130 | temp *= y; | ||
131 | |||
132 | temp >>= PRECISION; | ||
133 | |||
134 | //rb->fdprintf(filehandle,"%d\n", (fixed32)temp); | ||
135 | //rb->close(filehandle); | ||
136 | |||
137 | return (fixed32)temp; | ||
138 | } | ||
139 | |||
140 | #endif | ||
141 | //thanks MAD! | ||
142 | |||
143 | |||
144 | //mgg: special fixmul32 that does a 16.16 x 1.31 multiply that returns a 16.16 value. | ||
145 | //this is needed because the fft constants are all normalized to be less then 1 and can't fit into a 16 bit number | ||
146 | #ifdef CPU_ARM | ||
147 | |||
148 | # define fixmul32b(x, y) \ | ||
149 | ({ int32_t __hi; \ | ||
150 | uint32_t __lo; \ | ||
151 | int32_t __result; \ | ||
152 | asm ("smull %0, %1, %3, %4\n\t" \ | ||
153 | "movs %0, %0, lsr %5\n\t" \ | ||
154 | "adc %2, %0, %1, lsl %6" \ | ||
155 | : "=&r" (__lo), "=&r" (__hi), "=r" (__result) \ | ||
156 | : "%r" (x), "r" (y), \ | ||
157 | "M" (31), "M" (1) \ | ||
158 | : "cc"); \ | ||
159 | __result; \ | ||
160 | }) | ||
161 | #elif !defined(CPU_COLDFIRE) | ||
162 | static fixed32 fixmul32b(fixed32 x, fixed32 y) | ||
163 | { | ||
164 | fixed64 temp; | ||
165 | |||
166 | temp = x; | ||
167 | temp *= y; | ||
168 | |||
169 | temp >>= 31; //16+31-16 = 31 bits | ||
170 | |||
171 | return (fixed32)temp; | ||
172 | } | ||
173 | |||
174 | #endif | ||
175 | |||
176 | |||
177 | |||
178 | |||
179 | static fixed64 fixmul64byfixed(fixed64 x, fixed32 y) | ||
180 | { | ||
181 | |||
182 | //return x * y; | ||
183 | return (x * y); | ||
184 | // return (fixed64) fixmul32(Fixed32From64(x),y); | ||
185 | } | ||
186 | |||
187 | |||
188 | fixed32 fixdiv32(fixed32 x, fixed32 y) | ||
189 | { | ||
190 | fixed64 temp; | ||
191 | |||
192 | if(x == 0) | ||
193 | return 0; | ||
194 | if(y == 0) | ||
195 | return 0x7fffffff; | ||
196 | temp = x; | ||
197 | temp <<= PRECISION; | ||
198 | return (fixed32)(temp / y); | ||
199 | } | ||
200 | |||
201 | |||
202 | static fixed64 fixdiv64(fixed64 x, fixed64 y) | ||
203 | { | ||
204 | fixed64 temp; | ||
205 | |||
206 | if(x == 0) | ||
207 | return 0; | ||
208 | if(y == 0) | ||
209 | return 0x07ffffffffffffffLL; | ||
210 | temp = x; | ||
211 | temp <<= PRECISION64; | ||
212 | return (fixed64)(temp / y); | ||
213 | } | ||
214 | |||
215 | static fixed32 fixsqrt32(fixed32 x) | ||
216 | { | ||
217 | |||
218 | unsigned long r = 0, s, v = (unsigned long)x; | ||
219 | |||
220 | #define STEP(k) s = r + (1 << k * 2); r >>= 1; \ | ||
221 | if (s <= v) { v -= s; r |= (1 << k * 2); } | ||
222 | |||
223 | STEP(15); | ||
224 | STEP(14); | ||
225 | STEP(13); | ||
226 | STEP(12); | ||
227 | STEP(11); | ||
228 | STEP(10); | ||
229 | STEP(9); | ||
230 | STEP(8); | ||
231 | STEP(7); | ||
232 | STEP(6); | ||
233 | STEP(5); | ||
234 | STEP(4); | ||
235 | STEP(3); | ||
236 | STEP(2); | ||
237 | STEP(1); | ||
238 | STEP(0); | ||
239 | |||
240 | return (fixed32)(r << (PRECISION / 2)); | ||
241 | } | ||
242 | |||
243 | |||
244 | __inline fixed32 fixsin32(fixed32 x) | ||
245 | { | ||
246 | |||
247 | fixed64 x2, temp; | ||
248 | int sign = 1; | ||
249 | |||
250 | if(x < 0) | ||
251 | { | ||
252 | sign = -1; | ||
253 | x = -x; | ||
254 | } | ||
255 | while (x > 0x19220) | ||
256 | { | ||
257 | x -= M_PI_F; | ||
258 | sign = -sign; | ||
259 | } | ||
260 | if (x > 0x19220) | ||
261 | { | ||
262 | x = M_PI_F - x; | ||
263 | } | ||
264 | x2 = (fixed64)x * x; | ||
265 | x2 >>= PRECISION; | ||
266 | if(sign != 1) | ||
267 | { | ||
268 | x = -x; | ||
269 | } | ||
270 | /** | ||
271 | temp = ftofix32(-.0000000239f) * x2; | ||
272 | temp >>= PRECISION; | ||
273 | **/ | ||
274 | temp = 0; // PJJ | ||
275 | //temp = (temp + 0x0) * x2; //MGG: this can't possibly do anything? | ||
276 | //temp >>= PRECISION; | ||
277 | temp = (temp - 0xd) * x2; | ||
278 | temp >>= PRECISION; | ||
279 | temp = (temp + 0x222) * x2; | ||
280 | temp >>= PRECISION; | ||
281 | temp = (temp - 0x2aab) * x2; | ||
282 | temp >>= PRECISION; | ||
283 | temp += 0x10000; | ||
284 | temp = temp * x; | ||
285 | temp >>= PRECISION; | ||
286 | |||
287 | return (fixed32)(temp); | ||
288 | } | ||
289 | |||
290 | __inline fixed32 fixcos32(fixed32 x) | ||
291 | { | ||
292 | return fixsin32(x - (M_PI_F>>1))*-1; | ||
293 | } | ||
294 | |||
295 | |||
296 | /* Inverse gain of circular cordic rotation in s0.31 format. */ | ||
297 | static const long cordic_circular_gain = 0xb2458939; /* 0.607252929 */ | ||
298 | |||
299 | /* Table of values of atan(2^-i) in 0.32 format fractions of pi where pi = 0xffffffff / 2 */ | ||
300 | static const unsigned long atan_table[] = { | ||
301 | 0x1fffffff, /* +0.785398163 (or pi/4) */ | ||
302 | 0x12e4051d, /* +0.463647609 */ | ||
303 | 0x09fb385b, /* +0.244978663 */ | ||
304 | 0x051111d4, /* +0.124354995 */ | ||
305 | 0x028b0d43, /* +0.062418810 */ | ||
306 | 0x0145d7e1, /* +0.031239833 */ | ||
307 | 0x00a2f61e, /* +0.015623729 */ | ||
308 | 0x00517c55, /* +0.007812341 */ | ||
309 | 0x0028be53, /* +0.003906230 */ | ||
310 | 0x00145f2e, /* +0.001953123 */ | ||
311 | 0x000a2f98, /* +0.000976562 */ | ||
312 | 0x000517cc, /* +0.000488281 */ | ||
313 | 0x00028be6, /* +0.000244141 */ | ||
314 | 0x000145f3, /* +0.000122070 */ | ||
315 | 0x0000a2f9, /* +0.000061035 */ | ||
316 | 0x0000517c, /* +0.000030518 */ | ||
317 | 0x000028be, /* +0.000015259 */ | ||
318 | 0x0000145f, /* +0.000007629 */ | ||
319 | 0x00000a2f, /* +0.000003815 */ | ||
320 | 0x00000517, /* +0.000001907 */ | ||
321 | 0x0000028b, /* +0.000000954 */ | ||
322 | 0x00000145, /* +0.000000477 */ | ||
323 | 0x000000a2, /* +0.000000238 */ | ||
324 | 0x00000051, /* +0.000000119 */ | ||
325 | 0x00000028, /* +0.000000060 */ | ||
326 | 0x00000014, /* +0.000000030 */ | ||
327 | 0x0000000a, /* +0.000000015 */ | ||
328 | 0x00000005, /* +0.000000007 */ | ||
329 | 0x00000002, /* +0.000000004 */ | ||
330 | 0x00000001, /* +0.000000002 */ | ||
331 | 0x00000000, /* +0.000000001 */ | ||
332 | 0x00000000, /* +0.000000000 */ | ||
333 | }; | ||
334 | |||
335 | /** | ||
336 | * Implements sin and cos using CORDIC rotation. | ||
337 | * | ||
338 | * @param phase has range from 0 to 0xffffffff, representing 0 and | ||
339 | * 2*pi respectively. | ||
340 | * @param cos return address for cos | ||
341 | * @return sin of phase, value is a signed value from LONG_MIN to LONG_MAX, | ||
342 | * representing -1 and 1 respectively. | ||
343 | * | ||
344 | * Gives at least 24 bits precision (last 2-8 bits or so are probably off) | ||
345 | */ | ||
346 | static long fsincos(unsigned long phase, fixed32 *cos) | ||
347 | { | ||
348 | int32_t x, x1, y, y1; | ||
349 | unsigned long z, z1; | ||
350 | int i; | ||
351 | |||
352 | /* Setup initial vector */ | ||
353 | x = cordic_circular_gain; | ||
354 | y = 0; | ||
355 | z = phase; | ||
356 | |||
357 | /* The phase has to be somewhere between 0..pi for this to work right */ | ||
358 | if (z < 0xffffffff / 4) { | ||
359 | /* z in first quadrant, z += pi/2 to correct */ | ||
360 | x = -x; | ||
361 | z += 0xffffffff / 4; | ||
362 | } else if (z < 3 * (0xffffffff / 4)) { | ||
363 | /* z in third quadrant, z -= pi/2 to correct */ | ||
364 | z -= 0xffffffff / 4; | ||
365 | } else { | ||
366 | /* z in fourth quadrant, z -= 3pi/2 to correct */ | ||
367 | x = -x; | ||
368 | z -= 3 * (0xffffffff / 4); | ||
369 | } | ||
370 | |||
371 | /* Each iteration adds roughly 1-bit of extra precision */ | ||
372 | for (i = 0; i < 31; i++) { | ||
373 | x1 = x >> i; | ||
374 | y1 = y >> i; | ||
375 | z1 = atan_table[i]; | ||
376 | |||
377 | /* Decided which direction to rotate vector. Pivot point is pi/2 */ | ||
378 | if (z >= 0xffffffff / 4) { | ||
379 | x -= y1; | ||
380 | y += x1; | ||
381 | z -= z1; | ||
382 | } else { | ||
383 | x += y1; | ||
384 | y -= x1; | ||
385 | z += z1; | ||
386 | } | ||
387 | } | ||
388 | |||
389 | if (cos) | ||
390 | *cos = x; | ||
391 | |||
392 | return y; | ||
393 | } | ||
394 | |||
395 | |||
396 | |||
397 | /* | ||
398 | __inline fixed32 fixasin32(fixed32 x) | ||
399 | { | ||
400 | fixed64 temp; | ||
401 | int sign = 1; | ||
402 | |||
403 | if(x > 0x10000 || x < 0xffff0000) | ||
404 | { | ||
405 | return 0; | ||
406 | } | ||
407 | if(x < 0) | ||
408 | { | ||
409 | sign = -1; | ||
410 | x = -x; | ||
411 | } | ||
412 | temp = 0xffffffad * (fixed64)x; | ||
413 | temp >>= PRECISION; | ||
414 | temp = (temp + 0x1b5) * x; | ||
415 | temp >>= PRECISION; | ||
416 | temp = (temp - 0x460) * x; | ||
417 | temp >>= PRECISION; | ||
418 | temp = (temp + 0x7e9) * x; | ||
419 | temp >>= PRECISION; | ||
420 | temp = (temp - 0xcd8) * x; | ||
421 | temp >>= PRECISION; | ||
422 | temp = (temp + 0x16c7) * x; | ||
423 | temp >>= PRECISION; | ||
424 | temp = (temp - 0x36f0) * x; | ||
425 | temp >>= PRECISION; | ||
426 | temp = (temp + 0x19220) * fixsqrt32(0x10000 - x); | ||
427 | temp >>= PRECISION; | ||
428 | |||
429 | return sign * ((M_PI_F>>1) - (fixed32)temp); | ||
430 | } | ||
431 | */ | ||
432 | 32 | ||
433 | #define ALT_BITSTREAM_READER | 33 | #define ALT_BITSTREAM_READER |
434 | 34 | ||
@@ -528,98 +128,8 @@ static VLC_TYPE vlcbuf1[6144][2]; | |||
528 | static VLC_TYPE vlcbuf2[3584][2]; | 128 | static VLC_TYPE vlcbuf2[3584][2]; |
529 | static VLC_TYPE vlcbuf3[1536][2] IBSS_ATTR; //small so lets try iram | 129 | static VLC_TYPE vlcbuf3[1536][2] IBSS_ATTR; //small so lets try iram |
530 | 130 | ||
531 | //fixed32 window[BLOCK_MAX_SIZE * 2]; | 131 | |
532 | 132 | ||
533 | const fixed64 pow_table[] = | ||
534 | { | ||
535 | 0x10000LL,0x11f3dLL,0x14249LL,0x1699cLL,0x195bcLL,0x1c73dLL,0x1fec9LL,0x23d1dLL,0x2830bLL,0x2d182LL, | ||
536 | 0x3298bLL,0x38c53LL,0x3fb28LL,0x47783LL,0x5030aLL,0x59f98LL,0x64f40LL,0x71457LL,0x7f17bLL,0x8e99aLL, | ||
537 | 0xa0000LL,0xb385eLL,0xc96d9LL,0xe2019LL,0xfd954LL,0x11c865LL,0x13f3dfLL,0x166320LL,0x191e6eLL,0x1c2f10LL, | ||
538 | 0x1f9f6eLL,0x237b39LL,0x27cf8bLL,0x2cab1aLL,0x321e65LL,0x383bf0LL,0x3f1882LL,0x46cb6aLL,0x4f6eceLL,0x592006LL, | ||
539 | 0x640000LL,0x7033acLL,0x7de47eLL,0x8d40f6LL,0x9e7d44LL,0xb1d3f4LL,0xc786b7LL,0xdfdf43LL,0xfb304bLL,0x119d69aLL, | ||
540 | 0x13c3a4eLL,0x162d03aLL,0x18e1b70LL,0x1beaf00LL,0x1f52feeLL,0x2325760LL,0x276f514LL,0x2c3f220LL,0x31a5408LL, | ||
541 | 0x37b403cLL,0x3e80000LL,0x46204b8LL,0x4eaece8LL,0x58489a0LL,0x630e4a8LL,0x6f24788LL,0x7cb4328LL,0x8beb8a0LL, | ||
542 | 0x9cfe2f0LL,0xb026200LL,0xc5a4710LL,0xddc2240LL,0xf8d1260LL,0x1172d600LL,0x1393df60LL,0x15f769c0LL,0x18a592c0LL, | ||
543 | 0x1ba77540LL,0x1f074840LL,0x22d08280LL,0x27100000LL,0x2bd42f40LL,0x312d4100LL,0x372d6000LL,0x3de8ee80LL, | ||
544 | 0x4576cb80LL,0x4df09f80LL,0x57733600LL,0x621edd80LL,0x6e17d480LL,0x7b86c700LL,0x8a995700LL,0x9b82b800LL, | ||
545 | 0xae7c5c00LL,0xc3c6b900LL,0xdbaa2200LL,0xf677bc00LL,0x1148a9400LL,0x13648d200LL,0x15c251800LL,0x186a00000LL, | ||
546 | 0x1b649d800LL,0x1ebc48a00LL,0x227c5c000LL,0x26b195000LL,0x2b6a3f000LL,0x30b663c00LL,0x36a801c00LL,0x3d534a400LL, | ||
547 | 0x44cee4800LL,0x4d343c800LL,0x569fd6000LL,0x6131b2800LL,0x6d0db9800LL,0x7a5c33800LL,0x894a55000LL,0x9a0ad6000LL, | ||
548 | 0xacd69d000LL,0xc1ed84000LL,0xd9972f000LL,0xf42400000LL,0x111ee28000LL,0x1335ad6000LL,0x158db98000LL,0x182efd4000LL, | ||
549 | 0x1b22676000LL,0x1e71fe6000LL,0x2229014000LL,0x26540e8000LL,0x2b014f0000LL,0x3040a5c000LL,0x3623e60000LL,0x3cbf0fc000LL, | ||
550 | 0x4428940000LL,0x4c79a08000LL,0x55ce758000LL,0x6046c58000LL,0x6c06220000LL,0x7934728000LL,0x87fe7d0000LL,0x9896800000LL, | ||
551 | 0xab34d90000LL,0xc018c60000LL,0xd7893f0000LL,0xf1d5e40000LL,0x10f580a0000LL,0x13073f00000LL,0x1559a0c0000LL,0x17f48900000LL, | ||
552 | 0x1ae0d160000LL,0x1e286780000LL,0x21d66fc0000LL,0x25f769c0000LL,0x2a995c80000LL,0x2fcc0440000LL,0x35a10940000LL, | ||
553 | 0x3c2c3b80000LL,0x4383d500000LL,0x4bc0c780000LL,0x54ff0e80000LL,0x5f5e1000000LL,0x6b010780000LL,0x780f7c00000LL, | ||
554 | 0x86b5c800000LL,0x9725ae00000LL,0xa9970600000LL,0xbe487500000LL,0xd5804700000LL,0xef8d5a00000LL,0x10cc82e00000LL, | ||
555 | 0x12d940c00000LL,0x152605c00000LL,0x17baa2200000LL,0x1a9fd9c00000LL,0x1ddf82a00000LL,0x2184a5c00000LL,0x259ba5400000LL, | ||
556 | 0x2a3265400000LL,0x2f587cc00000LL,0x351f69000000LL,0x3b9aca000000LL,0x42e0a4800000LL,0x4b09ad800000LL, | ||
557 | 0x54319d000000LL,0x5e778d000000LL,0x69fe64000000LL,0x76ed49800000LL,0x85702c000000LL,0x95b858000000LL, | ||
558 | 0xa7fd1c000000LL,0xbc7c87000000LL,0xd37c3a000000LL,0xed4a55000000LL,0x10a3e82000000LL,0x12abb1a000000LL, | ||
559 | 0x14f2e7a000000LL,0x1781474000000LL,0x1a5f7f4000000LL,0x1d974de000000LL,0x2133a18000000LL | ||
560 | }; | ||
561 | |||
562 | const fixed32 pow_10_to_yover16[] ICONST_ATTR= | ||
563 | { | ||
564 | 0x10000,0x127a0,0x15562,0x18a39,0x1c73d,0x20db4,0x25f12,0x2bd09,0x3298b,0x3a6d9,0x4378b,0x4dea3, | ||
565 | 0x59f98,0x67e6b,0x77fbb,0x8a8de,0xa0000,0xb8c3e,0xd55d1,0xf6636,0x11c865,0x148906,0x17b6b8,0x1b625b, | ||
566 | 0x1f9f6e,0x248475,0x2a2b6e,0x30b25f,0x383bf0,0x40f02c,0x4afd4b,0x5698b0,0x640000,0x737a6b,0x855a26, | ||
567 | 0x99fe1f,0xb1d3f4,0xcd5a3e,0xed232b,0x111d78a,0x13c3a4e,0x16d2c94,0x1a5b24e,0x1e6f7b0,0x2325760, | ||
568 | 0x28961b4,0x2ede4ec,0x361f6dc,0x3e80000,0x482c830,0x5358580,0x603ed30,0x6f24788,0x8058670,0x9435fb0, | ||
569 | 0xab26b70,0xc5a4710,0xe43bdc0,0x1078f700,0x1305ace0,0x15f769c0,0x195dd100,0x1d4af120 | ||
570 | }; | ||
571 | |||
572 | const fixed32 pow_a_table[] = | ||
573 | { | ||
574 | 0x1004,0x1008,0x100c,0x1010,0x1014,0x1018,0x101c,0x1021,0x1025,0x1029,0x102d,0x1031,0x1036,0x103a, | ||
575 | 0x103e,0x1043,0x1047,0x104b,0x1050,0x1054,0x1059,0x105d,0x1062,0x1066,0x106b,0x106f,0x1074,0x1078, | ||
576 | 0x107d,0x1082,0x1086,0x108b,0x1090,0x1095,0x1099,0x109e,0x10a3,0x10a8,0x10ad,0x10b2,0x10b7,0x10bc, | ||
577 | 0x10c1,0x10c6,0x10cb,0x10d0,0x10d5,0x10da,0x10df,0x10e5,0x10ea,0x10ef,0x10f5,0x10fa,0x10ff,0x1105, | ||
578 | 0x110a,0x1110,0x1115,0x111b,0x1120,0x1126,0x112c,0x1131,0x1137,0x113d,0x1143,0x1149,0x114f,0x1155, | ||
579 | 0x115a,0x1161,0x1167,0x116d,0x1173,0x1179,0x117f,0x1186,0x118c,0x1192,0x1199,0x119f,0x11a6,0x11ac, | ||
580 | 0x11b3,0x11b9,0x11c0,0x11c7,0x11ce,0x11d4,0x11db,0x11e2,0x11e9,0x11f0,0x11f8,0x11ff,0x1206,0x120d, | ||
581 | 0x1215,0x121c,0x1223,0x122b,0x1233,0x123a,0x1242,0x124a,0x1251,0x1259,0x1261,0x1269,0x1271,0x127a, | ||
582 | 0x1282,0x128a,0x1293,0x129b,0x12a4,0x12ac,0x12b5,0x12be,0x12c7,0x12d0,0x12d9,0x12e2,0x12eb,0x12f4, | ||
583 | 0x12fe,0x1307 | ||
584 | }; | ||
585 | |||
586 | const fixed64 lsp_pow_e_table[] = | ||
587 | { | ||
588 | 0xf333f9deLL, 0xf0518db9LL, 0x0LL, 0x7e656b4fLL, 0x7999fcefLL, 0xf828c6dcLL, 0x0LL, | ||
589 | 0x3f32b5a7LL, 0x3cccfe78LL, 0xfc14636eLL, 0x0LL, 0x9f995ad4LL, 0x9e667f3cLL, 0xfe0a31b7LL, | ||
590 | 0x0LL, 0x4fccad6aLL, 0x4f333f9eLL, 0x7f0518dcLL, 0x0LL, 0x27e656b5LL, 0x27999fcfLL, | ||
591 | 0xbf828c6eLL, 0x0LL, 0x13f32b5aLL, 0x13cccfe7LL, 0xdfc14637LL, 0x0LL, 0x89f995adLL, | ||
592 | 0x9e667f4LL, 0x6fe0a31bLL, 0x0LL, 0x44fccad7LL, 0x4f333faLL, 0x37f0518eLL, 0x0LL, | ||
593 | 0xa27e656bLL, 0x827999fdLL, 0x1bf828c7LL, 0x0LL, 0xd13f32b6LL, 0x413cccfeLL, 0xdfc1463LL, | ||
594 | 0x0LL, 0xe89f995bLL, 0xa09e667fLL, 0x6fe0a32LL, 0x0LL, 0x744fccadLL, 0x504f3340LL, | ||
595 | 0x837f0519LL, 0x0LL, 0xba27e657LL, 0xa82799a0LL, 0xc1bf828cLL, 0x0LL, 0x5d13f32bLL, | ||
596 | 0xd413ccd0LL, 0x60dfc146LL, 0x0LL, 0xae89f996LL, 0x6a09e668LL, 0x306fe0a3LL, 0x0LL, | ||
597 | 0xd744fccbLL, 0xb504f334LL, 0x9837f052LL, 0x80000000LL, 0x6ba27e65LL, 0x5a82799aLL, | ||
598 | 0x4c1bf829LL, 0x40000000LL, 0x35d13f33LL, 0x2d413ccdLL, 0x260dfc14LL, 0x20000000LL, | ||
599 | 0x1ae89f99LL, 0x16a09e66LL, 0x1306fe0aLL, 0x10000000LL, 0xd744fcdLL, 0xb504f33LL, | ||
600 | 0x9837f05LL, 0x8000000LL, 0x6ba27e6LL, 0x5a8279aLL, 0x4c1bf83LL, 0x4000000LL, | ||
601 | 0x35d13f3LL, 0x2d413cdLL, 0x260dfc1LL, 0x2000000LL, 0x1ae89faLL, 0x16a09e6LL, | ||
602 | 0x1306fe1LL, 0x1000000LL, 0xd744fdLL, 0xb504f3LL, 0x9837f0LL, 0x800000LL, | ||
603 | 0x6ba27eLL, 0x5a827aLL, 0x4c1bf8LL, 0x400000LL, 0x35d13fLL, 0x2d413dLL, | ||
604 | 0x260dfcLL, 0x200000LL, 0x1ae8a0LL, 0x16a09eLL, 0x1306feLL, 0x100000LL, | ||
605 | 0xd7450LL, 0xb504fLL, 0x9837fLL, 0x80000LL, 0x6ba28LL, 0x5a828LL, 0x4c1c0LL, | ||
606 | 0x40000LL, 0x35d14LL, 0x2d414LL, 0x260e0LL, 0x20000LL, 0x1ae8aLL, 0x16a0aLL, | ||
607 | 0x13070LL, 0x10000LL, 0xd745LL, 0xb505LL, 0x9838LL, 0x8000LL, 0x6ba2LL, | ||
608 | 0x5a82LL, 0x4c1cLL, 0x4000LL, 0x35d1LL, 0x2d41LL, 0x260eLL, 0x2000LL, | ||
609 | 0x1ae9LL, 0x16a1LL, 0x1307LL, 0x1000LL, 0xd74LL, 0xb50LL, 0x983LL, 0x800LL, | ||
610 | 0x6baLL, 0x5a8LL, 0x4c2LL, 0x400LL, 0x35dLL, 0x2d4LL, 0x261LL, 0x200LL, 0x1afLL, | ||
611 | 0x16aLL, 0x130LL, 0x100LL, 0xd7LL, 0xb5LL, 0x98LL, 0x80LL, 0x6cLL, 0x5bLL, | ||
612 | 0x4cLL, 0x40LL, 0x36LL, 0x2dLL, 0x26LL, 0x20LL, 0x1bLL, 0x17LL, 0x13LL, | ||
613 | 0x10LL, 0xdLL, 0xbLL, 0xaLL, 0x8LL, 0x7LL, 0x6LL, 0x5LL, 0x4LL, 0x3LL, | ||
614 | 0x3LL, 0x2LL, 0x2LL, 0x2LL, 0x1LL, 0x1LL, 0x1LL, 0x1LL, 0x1LL, 0x1LL, | ||
615 | 0x1LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, | ||
616 | 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, | ||
617 | 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, | ||
618 | 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, | ||
619 | 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, | ||
620 | 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, 0x0LL, | ||
621 | 0x0LL, 0x0LL | ||
622 | }; | ||
623 | 133 | ||
624 | #include "wmadata.h" // PJJ | 134 | #include "wmadata.h" // PJJ |
625 | 135 | ||
@@ -630,12 +140,11 @@ const fixed64 lsp_pow_e_table[] = | |||
630 | int fft_inits(FFTContext *s, int nbits, int inverse) | 140 | int fft_inits(FFTContext *s, int nbits, int inverse) |
631 | { | 141 | { |
632 | int i, j, m, n; | 142 | int i, j, m, n; |
633 | fixed32 alpha, c1, s1, ct, st; | 143 | fixed32 c1, s1; |
634 | int s2; | 144 | int s2; |
635 | 145 | ||
636 | s->nbits = nbits; | 146 | s->nbits = nbits; |
637 | n = 1 << nbits; | 147 | n = 1 << nbits; |
638 | |||
639 | //s->exptab = exparray[10-nbits]; //not needed | 148 | //s->exptab = exparray[10-nbits]; //not needed |
640 | 149 | ||
641 | //s->exptab = av_malloc((n >> 1) * sizeof(FFTComplex)); | 150 | //s->exptab = av_malloc((n >> 1) * sizeof(FFTComplex)); |
@@ -666,9 +175,9 @@ int fft_inits(FFTContext *s, int nbits, int inverse) | |||
666 | fixed32 nfix = itofix32(n); | 175 | fixed32 nfix = itofix32(n); |
667 | fixed32 res = fixdiv32(ifix,nfix); //this is really bad here since nfix can be as large as 1024 ! | 176 | fixed32 res = fixdiv32(ifix,nfix); //this is really bad here since nfix can be as large as 1024 ! |
668 | //also, make this a shift, since its a fucking power of two divide | 177 | //also, make this a shift, since its a fucking power of two divide |
669 | alpha = fixmul32(TWO_M_PI_F, res); | 178 | //alpha = fixmul32(TWO_M_PI_F, res); |
670 | ct = fixcos32(alpha); //need to correct alpha for 0->2pi scale | 179 | //ct = fixcos32(alpha); //need to correct alpha for 0->2pi scale |
671 | st = fixsin32(alpha);// * s2; | 180 | //st = fixsin32(alpha);// * s2; |
672 | 181 | ||
673 | s1 = fsincos(res<<16, &c1); //does sin and cos in one pass! | 182 | s1 = fsincos(res<<16, &c1); //does sin and cos in one pass! |
674 | 183 | ||
@@ -718,10 +227,6 @@ int fft_inits(FFTContext *s, int nbits, int inverse) | |||
718 | qim = (by - ay);\ | 227 | qim = (by - ay);\ |
719 | } | 228 | } |
720 | 229 | ||
721 | //this goddamn butterfly could overflow and i'd neve rknow it... | ||
722 | //holy shit it was the fucking butterfly oh god this is the worst thing ever | ||
723 | |||
724 | |||
725 | 230 | ||
726 | int fft_calc_unscaled(FFTContext *s, FFTComplex *z) | 231 | int fft_calc_unscaled(FFTContext *s, FFTComplex *z) |
727 | { | 232 | { |
@@ -1612,18 +1117,6 @@ int wma_decode_init(WMADecodeContext* s, asf_waveformatex_t *wfx) | |||
1612 | init_coef_vlc(&s->coef_vlc[1], &s->run_table[1], &s->level_table[1], | 1117 | init_coef_vlc(&s->coef_vlc[1], &s->run_table[1], &s->level_table[1], |
1613 | &coef_vlcs[coef_vlc_table * 2 + 1], 1); | 1118 | &coef_vlcs[coef_vlc_table * 2 + 1], 1); |
1614 | 1119 | ||
1615 | //filehandle = rb->open("/log.txt", O_WRONLY|O_CREAT|O_APPEND); | ||
1616 | |||
1617 | |||
1618 | |||
1619 | //rb->fdprintf(filehandle,"In init:\n\nsample rate %d\nbit_rate %d\n version %d\n", s->sample_rate, s->bit_rate, s->version ); | ||
1620 | //rb->fdprintf(filehandle,"use_noise_coding %d \nframe_len %d\nframe_len_bits %d\n", s->use_noise_coding, s->frame_len, s->frame_len_bits); | ||
1621 | //rb->fdprintf(filehandle,"use_bit_reservoir %d\n use_variable_block_len %d\n use_exp_vlc %d\n",s->use_bit_reservoir, s->use_variable_block_len, s->use_exp_vlc); | ||
1622 | //rb->fdprintf(filehandle,"use_noise_coding %d\n byte_offset_bits %d\n use_exp_vlc %d\n",s->use_noise_coding, s->byte_offset_bits, s->use_exp_vlc); | ||
1623 | //rb->close(filehandle); | ||
1624 | |||
1625 | |||
1626 | |||
1627 | return 0; | 1120 | return 0; |
1628 | } | 1121 | } |
1629 | 1122 | ||
diff --git a/apps/codecs/libwma/wmafixed.c b/apps/codecs/libwma/wmafixed.c new file mode 100644 index 0000000000..6cb3d3c4a6 --- /dev/null +++ b/apps/codecs/libwma/wmafixed.c | |||
@@ -0,0 +1,350 @@ | |||
1 | //#include "asf.h" | ||
2 | #include "wmadec.h" | ||
3 | #include "wmafixed.h" | ||
4 | #include <codecs.h> | ||
5 | |||
6 | fixed64 IntTo64(int x){ | ||
7 | fixed64 res = 0; | ||
8 | unsigned char *p = (unsigned char *)&res; | ||
9 | |||
10 | #ifdef ROCKBOX_BIG_ENDIAN | ||
11 | p[5] = x & 0xff; | ||
12 | p[4] = (x & 0xff00)>>8; | ||
13 | p[3] = (x & 0xff0000)>>16; | ||
14 | p[2] = (x & 0xff000000)>>24; | ||
15 | #else | ||
16 | p[2] = x & 0xff; | ||
17 | p[3] = (x & 0xff00)>>8; | ||
18 | p[4] = (x & 0xff0000)>>16; | ||
19 | p[5] = (x & 0xff000000)>>24; | ||
20 | #endif | ||
21 | return res; | ||
22 | } | ||
23 | |||
24 | int IntFrom64(fixed64 x) | ||
25 | { | ||
26 | int res = 0; | ||
27 | unsigned char *p = (unsigned char *)&x; | ||
28 | |||
29 | #ifdef ROCKBOX_BIG_ENDIAN | ||
30 | res = p[5] | (p[4]<<8) | (p[3]<<16) | (p[2]<<24); | ||
31 | #else | ||
32 | res = p[2] | (p[3]<<8) | (p[4]<<16) | (p[5]<<24); | ||
33 | #endif | ||
34 | return res; | ||
35 | } | ||
36 | |||
37 | fixed32 Fixed32From64(fixed64 x) | ||
38 | { | ||
39 | return x & 0xFFFFFFFF; | ||
40 | } | ||
41 | |||
42 | fixed64 Fixed32To64(fixed32 x) | ||
43 | { | ||
44 | return (fixed64)x; | ||
45 | } | ||
46 | |||
47 | |||
48 | /* | ||
49 | Fixed precision multiply code. | ||
50 | |||
51 | */ | ||
52 | |||
53 | /*Sign-15.16 format */ | ||
54 | #ifdef CPU_ARM | ||
55 | /* these are defines in wmafixed.h*/ | ||
56 | |||
57 | |||
58 | #elif defined(CPU_COLDFIRE) | ||
59 | static inline int32_t fixmul32(int32_t x, int32_t y) | ||
60 | { | ||
61 | #if PRECISION != 16 | ||
62 | #warning Coldfire fixmul32() only works for PRECISION == 16 | ||
63 | #endif | ||
64 | int32_t t1; | ||
65 | asm ( | ||
66 | "mac.l %[x], %[y], %%acc0 \n" /* multiply */ | ||
67 | "mulu.l %[y], %[x] \n" /* get lower half, avoid emac stall */ | ||
68 | "movclr.l %%acc0, %[t1] \n" /* get higher half */ | ||
69 | "lsr.l #1, %[t1] \n" | ||
70 | "move.w %[t1], %[x] \n" | ||
71 | "swap %[x] \n" | ||
72 | : /* outputs */ | ||
73 | [t1]"=&d"(t1), | ||
74 | [x] "+d" (x) | ||
75 | : /* inputs */ | ||
76 | [y] "d" (y) | ||
77 | ); | ||
78 | return x; | ||
79 | } | ||
80 | #else | ||
81 | |||
82 | fixed32 fixmul32(fixed32 x, fixed32 y) | ||
83 | { | ||
84 | fixed64 temp; | ||
85 | temp = x; | ||
86 | temp *= y; | ||
87 | |||
88 | temp >>= PRECISION; | ||
89 | |||
90 | return (fixed32)temp; | ||
91 | } | ||
92 | |||
93 | |||
94 | |||
95 | /* | ||
96 | Special fixmul32 that does a 16.16 x 1.31 multiply that returns a 16.16 value. | ||
97 | this is needed because the fft constants are all normalized to be less then 1 | ||
98 | and can't fit into a 16 bit number without excessive rounding | ||
99 | |||
100 | |||
101 | */ | ||
102 | |||
103 | fixed32 fixmul32b(fixed32 x, fixed32 y) | ||
104 | { | ||
105 | fixed64 temp; | ||
106 | |||
107 | temp = x; | ||
108 | temp *= y; | ||
109 | |||
110 | temp >>= 31; //16+31-16 = 31 bits | ||
111 | |||
112 | return (fixed32)temp; | ||
113 | } | ||
114 | |||
115 | #endif | ||
116 | |||
117 | |||
118 | /* | ||
119 | Not performance senstitive code here | ||
120 | |||
121 | */ | ||
122 | |||
123 | |||
124 | fixed64 fixmul64byfixed(fixed64 x, fixed32 y) | ||
125 | { | ||
126 | |||
127 | //return x * y; | ||
128 | return (x * y); | ||
129 | // return (fixed64) fixmul32(Fixed32From64(x),y); | ||
130 | } | ||
131 | |||
132 | |||
133 | fixed32 fixdiv32(fixed32 x, fixed32 y) | ||
134 | { | ||
135 | fixed64 temp; | ||
136 | |||
137 | if(x == 0) | ||
138 | return 0; | ||
139 | if(y == 0) | ||
140 | return 0x7fffffff; | ||
141 | temp = x; | ||
142 | temp <<= PRECISION; | ||
143 | return (fixed32)(temp / y); | ||
144 | } | ||
145 | |||
146 | fixed64 fixdiv64(fixed64 x, fixed64 y) | ||
147 | { | ||
148 | fixed64 temp; | ||
149 | |||
150 | if(x == 0) | ||
151 | return 0; | ||
152 | if(y == 0) | ||
153 | return 0x07ffffffffffffffLL; | ||
154 | temp = x; | ||
155 | temp <<= PRECISION64; | ||
156 | return (fixed64)(temp / y); | ||
157 | } | ||
158 | |||
159 | fixed32 fixsqrt32(fixed32 x) | ||
160 | { | ||
161 | |||
162 | unsigned long r = 0, s, v = (unsigned long)x; | ||
163 | |||
164 | #define STEP(k) s = r + (1 << k * 2); r >>= 1; \ | ||
165 | if (s <= v) { v -= s; r |= (1 << k * 2); } | ||
166 | |||
167 | STEP(15); | ||
168 | STEP(14); | ||
169 | STEP(13); | ||
170 | STEP(12); | ||
171 | STEP(11); | ||
172 | STEP(10); | ||
173 | STEP(9); | ||
174 | STEP(8); | ||
175 | STEP(7); | ||
176 | STEP(6); | ||
177 | STEP(5); | ||
178 | STEP(4); | ||
179 | STEP(3); | ||
180 | STEP(2); | ||
181 | STEP(1); | ||
182 | STEP(0); | ||
183 | |||
184 | return (fixed32)(r << (PRECISION / 2)); | ||
185 | } | ||
186 | |||
187 | |||
188 | |||
189 | /* Inverse gain of circular cordic rotation in s0.31 format. */ | ||
190 | static const long cordic_circular_gain = 0xb2458939; /* 0.607252929 */ | ||
191 | |||
192 | /* Table of values of atan(2^-i) in 0.32 format fractions of pi where pi = 0xffffffff / 2 */ | ||
193 | static const unsigned long atan_table[] = { | ||
194 | 0x1fffffff, /* +0.785398163 (or pi/4) */ | ||
195 | 0x12e4051d, /* +0.463647609 */ | ||
196 | 0x09fb385b, /* +0.244978663 */ | ||
197 | 0x051111d4, /* +0.124354995 */ | ||
198 | 0x028b0d43, /* +0.062418810 */ | ||
199 | 0x0145d7e1, /* +0.031239833 */ | ||
200 | 0x00a2f61e, /* +0.015623729 */ | ||
201 | 0x00517c55, /* +0.007812341 */ | ||
202 | 0x0028be53, /* +0.003906230 */ | ||
203 | 0x00145f2e, /* +0.001953123 */ | ||
204 | 0x000a2f98, /* +0.000976562 */ | ||
205 | 0x000517cc, /* +0.000488281 */ | ||
206 | 0x00028be6, /* +0.000244141 */ | ||
207 | 0x000145f3, /* +0.000122070 */ | ||
208 | 0x0000a2f9, /* +0.000061035 */ | ||
209 | 0x0000517c, /* +0.000030518 */ | ||
210 | 0x000028be, /* +0.000015259 */ | ||
211 | 0x0000145f, /* +0.000007629 */ | ||
212 | 0x00000a2f, /* +0.000003815 */ | ||
213 | 0x00000517, /* +0.000001907 */ | ||
214 | 0x0000028b, /* +0.000000954 */ | ||
215 | 0x00000145, /* +0.000000477 */ | ||
216 | 0x000000a2, /* +0.000000238 */ | ||
217 | 0x00000051, /* +0.000000119 */ | ||
218 | 0x00000028, /* +0.000000060 */ | ||
219 | 0x00000014, /* +0.000000030 */ | ||
220 | 0x0000000a, /* +0.000000015 */ | ||
221 | 0x00000005, /* +0.000000007 */ | ||
222 | 0x00000002, /* +0.000000004 */ | ||
223 | 0x00000001, /* +0.000000002 */ | ||
224 | 0x00000000, /* +0.000000001 */ | ||
225 | 0x00000000, /* +0.000000000 */ | ||
226 | }; | ||
227 | |||
228 | |||
229 | /* | ||
230 | |||
231 | Below here functions do not use standard fixed precision! | ||
232 | */ | ||
233 | |||
234 | |||
235 | /** | ||
236 | * Implements sin and cos using CORDIC rotation. | ||
237 | * | ||
238 | * @param phase has range from 0 to 0xffffffff, representing 0 and | ||
239 | * 2*pi respectively. | ||
240 | * @param cos return address for cos | ||
241 | * @return sin of phase, value is a signed value from LONG_MIN to LONG_MAX, | ||
242 | * representing -1 and 1 respectively. | ||
243 | * | ||
244 | * Gives at least 24 bits precision (last 2-8 bits or so are probably off) | ||
245 | */ | ||
246 | long fsincos(unsigned long phase, fixed32 *cos) | ||
247 | { | ||
248 | int32_t x, x1, y, y1; | ||
249 | unsigned long z, z1; | ||
250 | int i; | ||
251 | |||
252 | /* Setup initial vector */ | ||
253 | x = cordic_circular_gain; | ||
254 | y = 0; | ||
255 | z = phase; | ||
256 | |||
257 | /* The phase has to be somewhere between 0..pi for this to work right */ | ||
258 | if (z < 0xffffffff / 4) { | ||
259 | /* z in first quadrant, z += pi/2 to correct */ | ||
260 | x = -x; | ||
261 | z += 0xffffffff / 4; | ||
262 | } else if (z < 3 * (0xffffffff / 4)) { | ||
263 | /* z in third quadrant, z -= pi/2 to correct */ | ||
264 | z -= 0xffffffff / 4; | ||
265 | } else { | ||
266 | /* z in fourth quadrant, z -= 3pi/2 to correct */ | ||
267 | x = -x; | ||
268 | z -= 3 * (0xffffffff / 4); | ||
269 | } | ||
270 | |||
271 | /* Each iteration adds roughly 1-bit of extra precision */ | ||
272 | for (i = 0; i < 31; i++) { | ||
273 | x1 = x >> i; | ||
274 | y1 = y >> i; | ||
275 | z1 = atan_table[i]; | ||
276 | |||
277 | /* Decided which direction to rotate vector. Pivot point is pi/2 */ | ||
278 | if (z >= 0xffffffff / 4) { | ||
279 | x -= y1; | ||
280 | y += x1; | ||
281 | z -= z1; | ||
282 | } else { | ||
283 | x += y1; | ||
284 | y -= x1; | ||
285 | z += z1; | ||
286 | } | ||
287 | } | ||
288 | |||
289 | if (cos) | ||
290 | *cos = x; | ||
291 | |||
292 | return y; | ||
293 | } | ||
294 | |||
295 | |||
296 | /* | ||
297 | Old trig functions. Still used in 1 place each. | ||
298 | |||
299 | */ | ||
300 | |||
301 | fixed32 fixsin32(fixed32 x) | ||
302 | { | ||
303 | |||
304 | fixed64 x2, temp; | ||
305 | int sign = 1; | ||
306 | |||
307 | if(x < 0) | ||
308 | { | ||
309 | sign = -1; | ||
310 | x = -x; | ||
311 | } | ||
312 | while (x > 0x19220) | ||
313 | { | ||
314 | x -= M_PI_F; | ||
315 | sign = -sign; | ||
316 | } | ||
317 | if (x > 0x19220) | ||
318 | { | ||
319 | x = M_PI_F - x; | ||
320 | } | ||
321 | x2 = (fixed64)x * x; | ||
322 | x2 >>= PRECISION; | ||
323 | if(sign != 1) | ||
324 | { | ||
325 | x = -x; | ||
326 | } | ||
327 | /** | ||
328 | temp = ftofix32(-.0000000239f) * x2; | ||
329 | temp >>= PRECISION; | ||
330 | **/ | ||
331 | temp = 0; // PJJ | ||
332 | //temp = (temp + 0x0) * x2; //MGG: this can't possibly do anything? | ||
333 | //temp >>= PRECISION; | ||
334 | temp = (temp - 0xd) * x2; | ||
335 | temp >>= PRECISION; | ||
336 | temp = (temp + 0x222) * x2; | ||
337 | temp >>= PRECISION; | ||
338 | temp = (temp - 0x2aab) * x2; | ||
339 | temp >>= PRECISION; | ||
340 | temp += 0x10000; | ||
341 | temp = temp * x; | ||
342 | temp >>= PRECISION; | ||
343 | |||
344 | return (fixed32)(temp); | ||
345 | } | ||
346 | |||
347 | fixed32 fixcos32(fixed32 x) | ||
348 | { | ||
349 | return fixsin32(x - (M_PI_F>>1))*-1; | ||
350 | } | ||
diff --git a/apps/codecs/libwma/wmafixed.h b/apps/codecs/libwma/wmafixed.h new file mode 100644 index 0000000000..878601d799 --- /dev/null +++ b/apps/codecs/libwma/wmafixed.h | |||
@@ -0,0 +1,92 @@ | |||
1 | /* fixed precision code. We use a combination of Sign 15.16 and Sign.31 | ||
2 | precision here. | ||
3 | |||
4 | The WMA decoder does not always follow this convention, and occasionally | ||
5 | renormalizes values to other formats in order to maximize precision. | ||
6 | However, only the two precisions above are provided in this file. | ||
7 | |||
8 | */ | ||
9 | |||
10 | |||
11 | #define PRECISION 16 | ||
12 | #define PRECISION64 16 | ||
13 | |||
14 | |||
15 | #define fixtof64(x) (float)((float)(x) / (float)(1 << PRECISION64)) //does not work on int64_t! | ||
16 | #define ftofix32(x) ((fixed32)((x) * (float)(1 << PRECISION) + ((x) < 0 ? -0.5 : 0.5))) | ||
17 | #define itofix64(x) (IntTo64(x)) | ||
18 | #define itofix32(x) ((x) << PRECISION) | ||
19 | #define fixtoi32(x) ((x) >> PRECISION) | ||
20 | #define fixtoi64(x) (IntFrom64(x)) | ||
21 | |||
22 | |||
23 | /*fixed functions*/ | ||
24 | |||
25 | fixed64 IntTo64(int x); | ||
26 | int IntFrom64(fixed64 x); | ||
27 | fixed32 Fixed32From64(fixed64 x); | ||
28 | fixed64 Fixed32To64(fixed32 x); | ||
29 | fixed64 fixmul64byfixed(fixed64 x, fixed32 y); | ||
30 | fixed32 fixdiv32(fixed32 x, fixed32 y); | ||
31 | fixed64 fixdiv64(fixed64 x, fixed64 y); | ||
32 | fixed32 fixsqrt32(fixed32 x); | ||
33 | fixed32 fixsin32(fixed32 x); | ||
34 | fixed32 fixcos32(fixed32 x); | ||
35 | long fsincos(unsigned long phase, fixed32 *cos); | ||
36 | |||
37 | |||
38 | |||
39 | |||
40 | |||
41 | #ifdef CPU_ARM | ||
42 | |||
43 | /* | ||
44 | Fixed precision multiply code ASM. | ||
45 | |||
46 | */ | ||
47 | |||
48 | /*Sign-15.16 format */ | ||
49 | |||
50 | #define fixmul32(x, y) \ | ||
51 | ({ int32_t __hi; \ | ||
52 | uint32_t __lo; \ | ||
53 | int32_t __result; \ | ||
54 | asm ("smull %0, %1, %3, %4\n\t" \ | ||
55 | "movs %0, %0, lsr %5\n\t" \ | ||
56 | "adc %2, %0, %1, lsl %6" \ | ||
57 | : "=&r" (__lo), "=&r" (__hi), "=r" (__result) \ | ||
58 | : "%r" (x), "r" (y), \ | ||
59 | "M" (PRECISION), "M" (32 - PRECISION) \ | ||
60 | : "cc"); \ | ||
61 | __result; \ | ||
62 | }) | ||
63 | |||
64 | /* | ||
65 | Special fixmul32 that does a 16.16 x 1.31 multiply that returns a 16.16 value. | ||
66 | this is needed because the fft constants are all normalized to be less then 1 | ||
67 | and can't fit into a 16 bit number without excessive rounding | ||
68 | |||
69 | |||
70 | */ | ||
71 | |||
72 | |||
73 | # define fixmul32b(x, y) \ | ||
74 | ({ int32_t __hi; \ | ||
75 | uint32_t __lo; \ | ||
76 | int32_t __result; \ | ||
77 | asm ("smull %0, %1, %3, %4\n\t" \ | ||
78 | "movs %0, %0, lsr %5\n\t" \ | ||
79 | "adc %2, %0, %1, lsl %6" \ | ||
80 | : "=&r" (__lo), "=&r" (__hi), "=r" (__result) \ | ||
81 | : "%r" (x), "r" (y), \ | ||
82 | "M" (31), "M" (1) \ | ||
83 | : "cc"); \ | ||
84 | __result; \ | ||
85 | }) | ||
86 | |||
87 | |||
88 | #else | ||
89 | fixed32 fixmul32(fixed32 x, fixed32 y); | ||
90 | fixed32 fixmul32b(fixed32 x, fixed32 y); | ||
91 | #endif | ||
92 | |||