typo
[libav.git] / tests / tiny_psnr.c
CommitLineData
67cbe681
MN
1/*
2 * Copyright (c) 2003 Michael Niedermayer <michaelni@gmx.at>
3 *
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Lesser General Public
6 * License as published by the Free Software Foundation; either
7 * version 2 of the License, or (at your option) any later version.
8 *
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Lesser General Public License for more details.
13 *
14 * You should have received a copy of the GNU Lesser General Public
15 * License along with this library; if not, write to the Free Software
5509bffa 16 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
67cbe681
MN
17 *
18 */
19
20#include <stdio.h>
ba96e97f 21#include <stdlib.h>
67cbe681 22#include <inttypes.h>
9e2a16e1 23#include <assert.h>
67cbe681
MN
24
25#define F 100
26#define SIZE 2048
27
0c90161f 28uint64_t exp16_table[21]={
9e2a16e1
MN
29 65537,
30 65538,
31 65540,
32 65544,
33 65552,
34 65568,
35 65600,
36 65664,
37 65793,
38 66050,
39 66568,
40 67616,
41 69763,
42 74262,
43 84150,
44 108051,
45 178145,
46 484249,
47 3578144,
48 195360063,
0c90161f 49 582360139072LL,
9e2a16e1
MN
50};
51#if 1
52// 16.16 fixpoint exp()
53static unsigned int exp16(unsigned int a){
54 int i;
55 int out= 1<<16;
56
57 for(i=19;i>=0;i--){
58 if(a&(1<<i))
59 out= (out*exp16_table[i] + (1<<15))>>16;
60 }
61
62 return out;
63}
64// 16.16 fixpoint log()
0c90161f 65static int64_t log16(uint64_t a){
9e2a16e1
MN
66 int i;
67 int out=0;
0c90161f
MN
68
69 if(a < 1<<16)
70 return -log16((1LL<<32) / a);
9e2a16e1 71 a<<=16;
115329f1 72
0c90161f 73 for(i=20;i>=0;i--){
8176bd1a
MN
74 int64_t b= exp16_table[i];
75 if(a<(b<<16)) continue;
9e2a16e1 76 out |= 1<<i;
8176bd1a 77 a = ((a/b)<<16) + (((a%b)<<16) + b/2)/b;
9e2a16e1
MN
78 }
79 return out;
80}
81
82#endif
67cbe681
MN
83static uint64_t int_sqrt(uint64_t a)
84{
85 uint64_t ret=0;
86 int s;
87 uint64_t ret_sq=0;
88
89 for(s=31; s>=0; s--){
90 uint64_t b= ret_sq + (1ULL<<(s*2)) + (ret<<s)*2;
91 if(b<=a){
92 ret_sq=b;
93 ret+= 1ULL<<s;
94 }
95 }
96 return ret;
97}
98
99int main(int argc,char* argv[]){
100 int i, j;
101 uint64_t sse=0;
102 uint64_t dev;
103 FILE *f[2];
104 uint8_t buf[2][SIZE];
9e2a16e1 105 uint64_t psnr;
ba96e97f 106 int len= argc<4 ? 1 : atoi(argv[3]);
0c90161f 107 int64_t max= (1<<(8*len))-1;
ba96e97f 108 int shift= argc<5 ? 0 : atoi(argv[4]);
b8889ea5 109 int skip_bytes = argc<6 ? 0 : atoi(argv[5]);
115329f1 110
0c90161f 111 if(argc<3){
b8889ea5
BL
112 printf("tiny_psnr <file1> <file2> [<elem size> [<shift> [<skip bytes>]]]\n");
113 printf("for wav files use the following:\n");
114 printf("./tiny_psnr file1.wav file2.wav 2 0 44 to skip the header.\n");
67cbe681
MN
115 return -1;
116 }
115329f1 117
0d6d0cf9
MN
118 f[0]= fopen(argv[1], "rb");
119 f[1]= fopen(argv[2], "rb");
ba96e97f 120 fseek(f[shift<0], shift < 0 ? -shift : shift, SEEK_SET);
67cbe681 121
b8889ea5
BL
122 fseek(f[0],skip_bytes,SEEK_CUR);
123 fseek(f[1],skip_bytes,SEEK_CUR);
124
67cbe681
MN
125 for(i=0;;){
126 if( fread(buf[0], SIZE, 1, f[0]) != 1) break;
127 if( fread(buf[1], SIZE, 1, f[1]) != 1) break;
115329f1 128
67cbe681 129 for(j=0; j<SIZE; i++,j++){
0c90161f
MN
130 int64_t a= buf[0][j];
131 int64_t b= buf[1][j];
132 if(len==2){
133 a= (int16_t)(a | (buf[0][++j]<<8));
134 b= (int16_t)(b | (buf[1][ j]<<8));
135 }
67cbe681
MN
136 sse += (a-b) * (a-b);
137 }
138 }
115329f1 139
eeaa742c 140 if(!i) i=1;
0c90161f 141 dev= int_sqrt( ((sse/i)*F*F) + (((sse%i)*F*F) + i/2)/i );
9e2a16e1 142 if(sse)
0c90161f 143 psnr= ((2*log16(max<<16) + log16(i) - log16(sse))*284619LL*F + (1<<31)) / (1LL<<32);
9e2a16e1
MN
144 else
145 psnr= 100*F-1; //floating point free infinity :)
115329f1
DB
146
147 printf("stddev:%3d.%02d PSNR:%2d.%02d bytes:%d\n",
148 (int)(dev/F), (int)(dev%F),
9e2a16e1 149 (int)(psnr/F), (int)(psnr%F),
ddbddce5 150 i*len);
67cbe681
MN
151 return 0;
152}
9e2a16e1
MN
153
154