1use c_vec::CVec;
4use get_error;
5use libc::{self, c_int, c_uint, c_void, size_t};
6use std::mem;
7use sys::gfx::imagefilter;
8
9pub fn mmx_detect() -> bool {
11 unsafe { imagefilter::SDL_imageFilterMMXdetect() == 1 }
12}
13
14pub fn mmx_off() {
16 unsafe { imagefilter::SDL_imageFilterMMXoff() }
17}
18
19pub fn mmx_on() {
21 unsafe { imagefilter::SDL_imageFilterMMXon() }
22}
23
24#[inline]
25fn cvec_with_size(sz: usize) -> CVec<u8> {
26 unsafe {
27 let p = libc::malloc(sz as size_t) as *mut u8;
28 CVec::new_with_dtor(p, sz, move |p| libc::free(p as *mut c_void))
29 }
30}
31
32pub fn add(src1: CVec<u8>, src2: CVec<u8>) -> Result<CVec<u8>, String> {
34 assert_eq!(src1.len(), src2.len());
35 let size = src1.len();
36 let dest = cvec_with_size(size);
37 let ret = unsafe {
38 imagefilter::SDL_imageFilterAdd(
39 mem::transmute(src1.get(0)),
40 mem::transmute(src2.get(0)),
41 mem::transmute(dest.get(0)),
42 size as c_uint,
43 )
44 };
45 if ret == 0 {
46 Ok(dest)
47 } else {
48 Err(get_error())
49 }
50}
51
52pub fn mean(src1: CVec<u8>, src2: CVec<u8>) -> Result<CVec<u8>, String> {
54 assert_eq!(src1.len(), src2.len());
55 let size = src1.len();
56 let dest = cvec_with_size(size);
57 let ret = unsafe {
58 imagefilter::SDL_imageFilterMean(
59 mem::transmute(src1.get(0)),
60 mem::transmute(src2.get(0)),
61 mem::transmute(dest.get(0)),
62 size as c_uint,
63 )
64 };
65 if ret == 0 {
66 Ok(dest)
67 } else {
68 Err(get_error())
69 }
70}
71
72pub fn sub(src1: CVec<u8>, src2: CVec<u8>) -> Result<CVec<u8>, String> {
74 assert_eq!(src1.len(), src2.len());
75 let size = src1.len();
76 let dest = cvec_with_size(size);
77 let ret = unsafe {
78 imagefilter::SDL_imageFilterSub(
79 mem::transmute(src1.get(0)),
80 mem::transmute(src2.get(0)),
81 mem::transmute(dest.get(0)),
82 size as c_uint,
83 )
84 };
85 if ret == 0 {
86 Ok(dest)
87 } else {
88 Err(get_error())
89 }
90}
91
92pub fn abs_diff(src1: CVec<u8>, src2: CVec<u8>) -> Result<CVec<u8>, String> {
94 assert_eq!(src1.len(), src2.len());
95 let size = src1.len();
96 let dest = cvec_with_size(size);
97 let ret = unsafe {
98 imagefilter::SDL_imageFilterAbsDiff(
99 mem::transmute(src1.get(0)),
100 mem::transmute(src2.get(0)),
101 mem::transmute(dest.get(0)),
102 size as c_uint,
103 )
104 };
105 if ret == 0 {
106 Ok(dest)
107 } else {
108 Err(get_error())
109 }
110}
111
112pub fn mult(src1: CVec<u8>, src2: CVec<u8>) -> Result<CVec<u8>, String> {
114 assert_eq!(src1.len(), src2.len());
115 let size = src1.len();
116 let dest = cvec_with_size(size);
117 let ret = unsafe {
118 imagefilter::SDL_imageFilterMult(
119 mem::transmute(src1.get(0)),
120 mem::transmute(src2.get(0)),
121 mem::transmute(dest.get(0)),
122 size as c_uint,
123 )
124 };
125 if ret == 0 {
126 Ok(dest)
127 } else {
128 Err(get_error())
129 }
130}
131
132pub fn mult_nor(src1: CVec<u8>, src2: CVec<u8>) -> Result<CVec<u8>, String> {
134 assert_eq!(src1.len(), src2.len());
135 let size = src1.len();
136 let dest = cvec_with_size(size);
137 let ret = unsafe {
138 imagefilter::SDL_imageFilterMultNor(
139 mem::transmute(src1.get(0)),
140 mem::transmute(src2.get(0)),
141 mem::transmute(dest.get(0)),
142 size as c_uint,
143 )
144 };
145 if ret == 0 {
146 Ok(dest)
147 } else {
148 Err(get_error())
149 }
150}
151
152pub fn mult_div_by2(src1: CVec<u8>, src2: CVec<u8>) -> Result<CVec<u8>, String> {
154 assert_eq!(src1.len(), src2.len());
155 let size = src1.len();
156 let dest = cvec_with_size(size);
157 let ret = unsafe {
158 imagefilter::SDL_imageFilterMultDivby2(
159 mem::transmute(src1.get(0)),
160 mem::transmute(src2.get(0)),
161 mem::transmute(dest.get(0)),
162 size as c_uint,
163 )
164 };
165 if ret == 0 {
166 Ok(dest)
167 } else {
168 Err(get_error())
169 }
170}
171
172pub fn mult_div_by4(src1: CVec<u8>, src2: CVec<u8>) -> Result<CVec<u8>, String> {
174 assert_eq!(src1.len(), src2.len());
175 let size = src1.len();
176 let dest = cvec_with_size(size);
177 let ret = unsafe {
178 imagefilter::SDL_imageFilterMultDivby4(
179 mem::transmute(src1.get(0)),
180 mem::transmute(src2.get(0)),
181 mem::transmute(dest.get(0)),
182 size as c_uint,
183 )
184 };
185 if ret == 0 {
186 Ok(dest)
187 } else {
188 Err(get_error())
189 }
190}
191
192pub fn bit_and(src1: CVec<u8>, src2: CVec<u8>) -> Result<CVec<u8>, String> {
194 assert_eq!(src1.len(), src2.len());
195 let size = src1.len();
196 let dest = cvec_with_size(size);
197 let ret = unsafe {
198 imagefilter::SDL_imageFilterBitAnd(
199 mem::transmute(src1.get(0)),
200 mem::transmute(src2.get(0)),
201 mem::transmute(dest.get(0)),
202 size as c_uint,
203 )
204 };
205 if ret == 0 {
206 Ok(dest)
207 } else {
208 Err(get_error())
209 }
210}
211
212pub fn bit_or(src1: CVec<u8>, src2: CVec<u8>) -> Result<CVec<u8>, String> {
214 assert_eq!(src1.len(), src2.len());
215 let size = src1.len();
216 let dest = cvec_with_size(size);
217 let ret = unsafe {
218 imagefilter::SDL_imageFilterBitOr(
219 mem::transmute(src1.get(0)),
220 mem::transmute(src2.get(0)),
221 mem::transmute(dest.get(0)),
222 size as c_uint,
223 )
224 };
225 if ret == 0 {
226 Ok(dest)
227 } else {
228 Err(get_error())
229 }
230}
231
232pub fn div(src1: CVec<u8>, src2: CVec<u8>) -> Result<CVec<u8>, String> {
234 assert_eq!(src1.len(), src2.len());
235 let size = src1.len();
236 let dest = cvec_with_size(size);
237 let ret = unsafe {
238 imagefilter::SDL_imageFilterDiv(
239 mem::transmute(src1.get(0)),
240 mem::transmute(src2.get(0)),
241 mem::transmute(dest.get(0)),
242 size as c_uint,
243 )
244 };
245 if ret == 0 {
246 Ok(dest)
247 } else {
248 Err(get_error())
249 }
250}
251
252pub fn bit_negation(src1: CVec<u8>) -> Result<CVec<u8>, String> {
254 let size = src1.len();
255 let dest = cvec_with_size(size);
256 let ret = unsafe {
257 imagefilter::SDL_imageFilterBitNegation(
258 mem::transmute(src1.get(0)),
259 mem::transmute(dest.get(0)),
260 size as c_uint,
261 )
262 };
263 if ret == 0 {
264 Ok(dest)
265 } else {
266 Err(get_error())
267 }
268}
269
270pub fn add_byte(src1: CVec<u8>, c: u8) -> Result<CVec<u8>, String> {
272 let size = src1.len();
273 let dest = cvec_with_size(size);
274 let ret = unsafe {
275 imagefilter::SDL_imageFilterAddByte(
276 mem::transmute(src1.get(0)),
277 mem::transmute(dest.get(0)),
278 size as c_uint,
279 c,
280 )
281 };
282 if ret == 0 {
283 Ok(dest)
284 } else {
285 Err(get_error())
286 }
287}
288
289pub fn add_uint(src1: CVec<u8>, c: u32) -> Result<CVec<u8>, String> {
291 let size = src1.len();
292 let dest = cvec_with_size(size);
293 let ret = unsafe {
294 imagefilter::SDL_imageFilterAddUint(
295 mem::transmute(src1.get(0)),
296 mem::transmute(dest.get(0)),
297 size as c_uint,
298 c,
299 )
300 };
301 if ret == 0 {
302 Ok(dest)
303 } else {
304 Err(get_error())
305 }
306}
307
308pub fn add_byte_to_half(src1: CVec<u8>, c: u8) -> Result<CVec<u8>, String> {
310 let size = src1.len();
311 let dest = cvec_with_size(size);
312 let ret = unsafe {
313 imagefilter::SDL_imageFilterAddByteToHalf(
314 mem::transmute(src1.get(0)),
315 mem::transmute(dest.get(0)),
316 size as c_uint,
317 c,
318 )
319 };
320 if ret == 0 {
321 Ok(dest)
322 } else {
323 Err(get_error())
324 }
325}
326
327pub fn sub_byte(src1: CVec<u8>, c: u8) -> Result<CVec<u8>, String> {
329 let size = src1.len();
330 let dest = cvec_with_size(size);
331 let ret = unsafe {
332 imagefilter::SDL_imageFilterSubByte(
333 mem::transmute(src1.get(0)),
334 mem::transmute(dest.get(0)),
335 size as c_uint,
336 c,
337 )
338 };
339 if ret == 0 {
340 Ok(dest)
341 } else {
342 Err(get_error())
343 }
344}
345
346pub fn sub_uint(src1: CVec<u8>, c: u32) -> Result<CVec<u8>, String> {
348 let size = src1.len();
349 let dest = cvec_with_size(size);
350 let ret = unsafe {
351 imagefilter::SDL_imageFilterSubUint(
352 mem::transmute(src1.get(0)),
353 mem::transmute(dest.get(0)),
354 size as c_uint,
355 c,
356 )
357 };
358 if ret == 0 {
359 Ok(dest)
360 } else {
361 Err(get_error())
362 }
363}
364
365pub fn shift_right(src1: CVec<u8>, n: u8) -> Result<CVec<u8>, String> {
367 let size = src1.len();
368 let dest = cvec_with_size(size);
369 let ret = unsafe {
370 imagefilter::SDL_imageFilterShiftRight(
371 mem::transmute(src1.get(0)),
372 mem::transmute(dest.get(0)),
373 size as c_uint,
374 n,
375 )
376 };
377 if ret == 0 {
378 Ok(dest)
379 } else {
380 Err(get_error())
381 }
382}
383
384pub fn shift_right_uint(src1: CVec<u8>, n: u8) -> Result<CVec<u8>, String> {
386 let size = src1.len();
387 let dest = cvec_with_size(size);
388 let ret = unsafe {
389 imagefilter::SDL_imageFilterShiftRightUint(
390 mem::transmute(src1.get(0)),
391 mem::transmute(dest.get(0)),
392 size as c_uint,
393 n,
394 )
395 };
396 if ret == 0 {
397 Ok(dest)
398 } else {
399 Err(get_error())
400 }
401}
402
403pub fn mult_by_byte(src1: CVec<u8>, c: u8) -> Result<CVec<u8>, String> {
405 let size = src1.len();
406 let dest = cvec_with_size(size);
407 let ret = unsafe {
408 imagefilter::SDL_imageFilterMultByByte(
409 mem::transmute(src1.get(0)),
410 mem::transmute(dest.get(0)),
411 size as c_uint,
412 c,
413 )
414 };
415 if ret == 0 {
416 Ok(dest)
417 } else {
418 Err(get_error())
419 }
420}
421
422pub fn shift_right_and_mult_by_byte(src1: CVec<u8>, n: u8, c: u8) -> Result<CVec<u8>, String> {
424 let size = src1.len();
425 let dest = cvec_with_size(size);
426 let ret = unsafe {
427 imagefilter::SDL_imageFilterShiftRightAndMultByByte(
428 mem::transmute(src1.get(0)),
429 mem::transmute(dest.get(0)),
430 size as c_uint,
431 n,
432 c,
433 )
434 };
435 if ret == 0 {
436 Ok(dest)
437 } else {
438 Err(get_error())
439 }
440}
441
442pub fn shift_left_byte(src1: CVec<u8>, n: u8) -> Result<CVec<u8>, String> {
444 let size = src1.len();
445 let dest = cvec_with_size(size);
446 let ret = unsafe {
447 imagefilter::SDL_imageFilterShiftLeftByte(
448 mem::transmute(src1.get(0)),
449 mem::transmute(dest.get(0)),
450 size as c_uint,
451 n,
452 )
453 };
454 if ret == 0 {
455 Ok(dest)
456 } else {
457 Err(get_error())
458 }
459}
460
461pub fn shift_left_uint(src1: CVec<u8>, n: u8) -> Result<CVec<u8>, String> {
463 let size = src1.len();
464 let dest = cvec_with_size(size);
465 let ret = unsafe {
466 imagefilter::SDL_imageFilterShiftLeftUint(
467 mem::transmute(src1.get(0)),
468 mem::transmute(dest.get(0)),
469 size as c_uint,
470 n,
471 )
472 };
473 if ret == 0 {
474 Ok(dest)
475 } else {
476 Err(get_error())
477 }
478}
479
480pub fn shift_left(src1: CVec<u8>, n: u8) -> Result<CVec<u8>, String> {
482 let size = src1.len();
483 let dest = cvec_with_size(size);
484 let ret = unsafe {
485 imagefilter::SDL_imageFilterShiftLeft(
486 mem::transmute(src1.get(0)),
487 mem::transmute(dest.get(0)),
488 size as c_uint,
489 n,
490 )
491 };
492 if ret == 0 {
493 Ok(dest)
494 } else {
495 Err(get_error())
496 }
497}
498
499pub fn binarize_using_threshold(src1: CVec<u8>, t: u8) -> Result<CVec<u8>, String> {
501 let size = src1.len();
502 let dest = cvec_with_size(size);
503 let ret = unsafe {
504 imagefilter::SDL_imageFilterBinarizeUsingThreshold(
505 mem::transmute(src1.get(0)),
506 mem::transmute(dest.get(0)),
507 size as c_uint,
508 t,
509 )
510 };
511 if ret == 0 {
512 Ok(dest)
513 } else {
514 Err(get_error())
515 }
516}
517
518pub fn clip_to_range(src1: CVec<u8>, tmin: u8, tmax: u8) -> Result<CVec<u8>, String> {
520 let size = src1.len();
521 let dest = cvec_with_size(size);
522 let ret = unsafe {
523 imagefilter::SDL_imageFilterClipToRange(
524 mem::transmute(src1.get(0)),
525 mem::transmute(dest.get(0)),
526 size as c_uint,
527 tmin,
528 tmax,
529 )
530 };
531 if ret == 0 {
532 Ok(dest)
533 } else {
534 Err(get_error())
535 }
536}
537
538pub fn normalize_linear(
540 src1: CVec<u8>,
541 cmin: i32,
542 cmax: i32,
543 nmin: i32,
544 nmax: i32,
545) -> Result<CVec<u8>, String> {
546 let size = src1.len();
547 let dest = cvec_with_size(size);
548 let ret = unsafe {
549 imagefilter::SDL_imageFilterNormalizeLinear(
550 mem::transmute(src1.get(0)),
551 mem::transmute(dest.get(0)),
552 size as c_uint,
553 cmin as c_int,
554 cmax as c_int,
555 nmin as c_int,
556 nmax as c_int,
557 )
558 };
559 if ret == 0 {
560 Ok(dest)
561 } else {
562 Err(get_error())
563 }
564}