home *** CD-ROM | disk | FTP | other *** search
/ OS/2 Shareware BBS: 10 Tools / 10-Tools.zip / wvis0626.zip / warpvision_20020626.zip / libavcodec / i386 / dsputil_mmx_avg.h < prev    next >
Text File  |  2002-06-19  |  9KB  |  297 lines

  1. /*
  2.  * DSP utils : average functions are compiled twice for 3dnow/mmx2
  3.  * Copyright (c) 2000, 2001 Fabrice Bellard.
  4.  * Copyright (c) 2002 Michael Niedermayer
  5.  *
  6.  * This library is free software; you can redistribute it and/or
  7.  * modify it under the terms of the GNU Lesser General Public
  8.  * License as published by the Free Software Foundation; either
  9.  * version 2 of the License, or (at your option) any later version.
  10.  *
  11.  * This library is distributed in the hope that it will be useful,
  12.  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  13.  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
  14.  * Lesser General Public License for more details.
  15.  *
  16.  * You should have received a copy of the GNU Lesser General Public
  17.  * License along with this library; if not, write to the Free Software
  18.  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
  19.  *
  20.  * MMX optimization by Nick Kurshev <nickols_k@mail.ru>
  21.  * mostly rewritten by Michael Niedermayer <michaelni@gmx.at>
  22.  * and improved by Zdenek Kabelac <kabi@users.sf.net>
  23.  */
  24.  
  25. /* XXX: we use explicit registers to avoid a gcc 2.95.2 register asm
  26.    clobber bug - now it will work with 2.95.2 and also with -fPIC
  27.  */
  28. static void DEF(put_pixels_x2)(UINT8 *block, const UINT8 *pixels, int line_size, int h)
  29. {
  30.     __asm __volatile(
  31.     "lea (%3, %3), %%eax        \n\t"
  32.     "1:                \n\t"
  33.     "movq (%1), %%mm0        \n\t"
  34.     "movq (%1, %3), %%mm1        \n\t"
  35.     PAVGB" 1(%1), %%mm0        \n\t"
  36.     PAVGB" 1(%1, %3), %%mm1        \n\t"
  37.     "movq %%mm0, (%2)        \n\t"
  38.     "movq %%mm1, (%2, %3)        \n\t"
  39.     "addl %%eax, %1            \n\t"
  40.     "addl %%eax, %2            \n\t"
  41.     "movq (%1), %%mm0        \n\t"
  42.     "movq (%1, %3), %%mm1        \n\t"
  43.     PAVGB" 1(%1), %%mm0        \n\t"
  44.     PAVGB" 1(%1, %3), %%mm1        \n\t"
  45.     "addl %%eax, %1            \n\t"
  46.     "movq %%mm0, (%2)        \n\t"
  47.     "movq %%mm1, (%2, %3)        \n\t"
  48.     "addl %%eax, %2            \n\t"
  49.     "subl $4, %0            \n\t"
  50.     "jnz 1b                \n\t"
  51.     :"+g"(h), "+S"(pixels), "+D"(block)
  52.     :"r" (line_size)
  53.     :"%eax", "memory");
  54. }
  55.  
  56. /* GL: this function does incorrect rounding if overflow */
  57. static void DEF(put_no_rnd_pixels_x2)(UINT8 *block, const UINT8 *pixels, int line_size, int h)
  58. {
  59.     MOVQ_BONE(mm6);
  60.     __asm __volatile(
  61.     "lea (%3, %3), %%eax        \n\t"
  62.     "1:                \n\t"
  63.     "movq (%1), %%mm0        \n\t"
  64.     "movq (%1, %3), %%mm2        \n\t"
  65.     "movq 1(%1), %%mm1        \n\t"
  66.     "movq 1(%1, %3), %%mm3        \n\t"
  67.     "addl %%eax, %1            \n\t"
  68.     "psubusb %%mm6, %%mm0        \n\t"
  69.     "psubusb %%mm6, %%mm2        \n\t"
  70.     PAVGB" %%mm1, %%mm0        \n\t"
  71.     PAVGB" %%mm3, %%mm2        \n\t"
  72.     "movq %%mm0, (%2)        \n\t"
  73.     "movq %%mm2, (%2, %3)        \n\t"
  74.     "movq (%1), %%mm0        \n\t"
  75.     "movq 1(%1), %%mm1        \n\t"
  76.     "movq (%1, %3), %%mm2        \n\t"
  77.     "movq 1(%1, %3), %%mm3        \n\t"
  78.     "addl %%eax, %2            \n\t"
  79.     "addl %%eax, %1            \n\t"
  80.     "psubusb %%mm6, %%mm0        \n\t"
  81.     "psubusb %%mm6, %%mm2        \n\t"
  82.     PAVGB" %%mm1, %%mm0        \n\t"
  83.     PAVGB" %%mm3, %%mm2        \n\t"
  84.     "movq %%mm0, (%2)        \n\t"
  85.     "movq %%mm2, (%2, %3)        \n\t"
  86.     "addl %%eax, %2            \n\t"
  87.     "subl $4, %0            \n\t"
  88.     "jnz 1b                \n\t"
  89.     :"+g"(h), "+S"(pixels), "+D"(block)
  90.     :"r" (line_size)
  91.     :"%eax", "memory");
  92. }
  93.  
  94. static void DEF(put_pixels_y2)(UINT8 *block, const UINT8 *pixels, int line_size, int h)
  95. {
  96.     __asm __volatile(
  97.     "lea (%3, %3), %%eax        \n\t"
  98.     "movq (%1), %%mm0        \n\t"
  99.     "subl %3, %2            \n\t"
  100.     "1:                \n\t"
  101.     "movq (%1, %3), %%mm1        \n\t"
  102.     "movq (%1, %%eax), %%mm2    \n\t"
  103.     "addl %%eax, %1            \n\t"
  104.     PAVGB" %%mm1, %%mm0        \n\t"
  105.     PAVGB" %%mm2, %%mm1        \n\t"
  106.     "movq %%mm0, (%2, %3)        \n\t"
  107.     "movq %%mm1, (%2, %%eax)    \n\t"
  108.     "movq (%1, %3), %%mm1        \n\t"
  109.     "movq (%1, %%eax), %%mm0    \n\t"
  110.     "addl %%eax, %2            \n\t"
  111.     "addl %%eax, %1            \n\t"
  112.     PAVGB" %%mm1, %%mm2        \n\t"
  113.     PAVGB" %%mm0, %%mm1        \n\t"
  114.     "movq %%mm2, (%2, %3)        \n\t"
  115.     "movq %%mm1, (%2, %%eax)    \n\t"
  116.     "addl %%eax, %2            \n\t"
  117.     "subl $4, %0            \n\t"
  118.     "jnz 1b                \n\t"
  119.     :"+g"(h), "+S"(pixels), "+D" (block)
  120.     :"r" (line_size)
  121.     :"%eax", "memory");
  122. }
  123.  
  124. /* GL: this function does incorrect rounding if overflow */
  125. static void DEF(put_no_rnd_pixels_y2)(UINT8 *block, const UINT8 *pixels, int line_size, int h)
  126. {
  127.     MOVQ_BONE(mm6);
  128.     __asm __volatile(
  129.     "lea (%3, %3), %%eax        \n\t"
  130.     "movq (%1), %%mm0        \n\t"
  131.     "subl %3, %2            \n\t"
  132.     "1:                \n\t"
  133.     "movq (%1, %3), %%mm1        \n\t"
  134.     "movq (%1, %%eax), %%mm2    \n\t"
  135.     "addl %%eax, %1            \n\t"
  136.     "psubusb %%mm6, %%mm1        \n\t"
  137.     PAVGB" %%mm1, %%mm0        \n\t"
  138.     PAVGB" %%mm2, %%mm1        \n\t"
  139.     "movq %%mm0, (%2, %3)        \n\t"
  140.     "movq %%mm1, (%2, %%eax)    \n\t"
  141.     "movq (%1, %3), %%mm1        \n\t"
  142.     "movq (%1, %%eax), %%mm0    \n\t"
  143.     "addl %%eax, %2            \n\t"
  144.     "addl %%eax, %1            \n\t"
  145.     "psubusb %%mm6, %%mm1        \n\t"
  146.     PAVGB" %%mm1, %%mm2        \n\t"
  147.     PAVGB" %%mm0, %%mm1        \n\t"
  148.     "movq %%mm2, (%2, %3)        \n\t"
  149.     "movq %%mm1, (%2, %%eax)    \n\t"
  150.     "addl %%eax, %2            \n\t"
  151.     "subl $4, %0            \n\t"
  152.     "jnz 1b                \n\t"
  153.     :"+g"(h), "+S"(pixels), "+D" (block)
  154.     :"r" (line_size)
  155.     :"%eax", "memory");
  156. }
  157.  
  158. static void DEF(avg_pixels)(UINT8 *block, const UINT8 *pixels, int line_size, int h)
  159. {
  160.     __asm __volatile(
  161.     "lea (%3, %3), %%eax        \n\t"
  162.     "1:                \n\t"
  163.     "movq (%2), %%mm0        \n\t"
  164.     "movq (%2, %3), %%mm1        \n\t"
  165.     PAVGB" (%1), %%mm0        \n\t"
  166.     PAVGB" (%1, %3), %%mm1        \n\t"
  167.     "movq %%mm0, (%2)        \n\t"
  168.     "movq %%mm1, (%2, %3)        \n\t"
  169.     "addl %%eax, %1            \n\t"
  170.     "addl %%eax, %2            \n\t"
  171.     "movq (%2), %%mm0        \n\t"
  172.     "movq (%2, %3), %%mm1        \n\t"
  173.     PAVGB" (%1), %%mm0        \n\t"
  174.     PAVGB" (%1, %3), %%mm1        \n\t"
  175.     "addl %%eax, %1            \n\t"
  176.     "movq %%mm0, (%2)        \n\t"
  177.     "movq %%mm1, (%2, %3)        \n\t"
  178.     "addl %%eax, %2            \n\t"
  179.     "subl $4, %0            \n\t"
  180.     "jnz 1b                \n\t"
  181.     :"+g"(h), "+S"(pixels), "+D"(block)
  182.     :"r" (line_size)
  183.     :"%eax", "memory");
  184. }
  185.  
  186. static void DEF(avg_pixels_x2)(UINT8 *block, const UINT8 *pixels, int line_size, int h)
  187. {
  188.     __asm __volatile(
  189.     "lea (%3, %3), %%eax        \n\t"
  190.     "1:                \n\t"
  191.     "movq (%1), %%mm0        \n\t"
  192.     "movq (%1, %3), %%mm2        \n\t"
  193.     PAVGB" 1(%1), %%mm0        \n\t"
  194.     PAVGB" 1(%1, %3), %%mm2        \n\t"
  195.     PAVGB" (%2), %%mm0        \n\t"
  196.     PAVGB" (%2, %3), %%mm2        \n\t"
  197.     "addl %%eax, %1            \n\t"
  198.     "movq %%mm0, (%2)        \n\t"
  199.     "movq %%mm2, (%2, %3)        \n\t"
  200.     "movq (%1), %%mm0        \n\t"
  201.     "movq (%1, %3), %%mm2        \n\t"
  202.     PAVGB" 1(%1), %%mm0        \n\t"
  203.     PAVGB" 1(%1, %3), %%mm2        \n\t"
  204.     "addl %%eax, %2            \n\t"
  205.     "addl %%eax, %1            \n\t"
  206.     PAVGB" (%2), %%mm0        \n\t"
  207.     PAVGB" (%2, %3), %%mm2        \n\t"
  208.     "movq %%mm0, (%2)        \n\t"
  209.     "movq %%mm2, (%2, %3)        \n\t"
  210.     "addl %%eax, %2            \n\t"
  211.     "subl $4, %0            \n\t"
  212.     "jnz 1b                \n\t"
  213.     :"+g"(h), "+S"(pixels), "+D"(block)
  214.     :"r" (line_size)
  215.     :"%eax", "memory");
  216. }
  217.  
  218. static void DEF(avg_pixels_y2)(UINT8 *block, const UINT8 *pixels, int line_size, int h)
  219. {
  220.     __asm __volatile(
  221.     "lea (%3, %3), %%eax        \n\t"
  222.     "movq (%1), %%mm0        \n\t"
  223.     "subl %3, %2            \n\t"
  224.     "1:                \n\t"
  225.     "movq (%1, %3), %%mm1        \n\t"
  226.     "movq (%1, %%eax), %%mm2    \n\t"
  227.     "addl %%eax, %1            \n\t"
  228.     PAVGB" %%mm1, %%mm0        \n\t"
  229.     PAVGB" %%mm2, %%mm1        \n\t"
  230.     "movq (%2, %3), %%mm3        \n\t"
  231.     "movq (%2, %%eax), %%mm4    \n\t"
  232.     PAVGB" %%mm3, %%mm0        \n\t"
  233.     PAVGB" %%mm4, %%mm1        \n\t"
  234.     "movq %%mm0, (%2, %3)        \n\t"
  235.     "movq %%mm1, (%2, %%eax)    \n\t"
  236.     "movq (%1, %3), %%mm1        \n\t"
  237.     "movq (%1, %%eax), %%mm0    \n\t"
  238.     PAVGB" %%mm1, %%mm2        \n\t"
  239.     PAVGB" %%mm0, %%mm1        \n\t"
  240.     "addl %%eax, %2            \n\t"
  241.     "addl %%eax, %1            \n\t"
  242.     "movq (%2, %3), %%mm3        \n\t"
  243.     "movq (%2, %%eax), %%mm4    \n\t"
  244.     PAVGB" %%mm3, %%mm2        \n\t"
  245.     PAVGB" %%mm4, %%mm1        \n\t"
  246.     "movq %%mm2, (%2, %3)        \n\t"
  247.     "movq %%mm1, (%2, %%eax)    \n\t"
  248.     "addl %%eax, %2            \n\t"
  249.     "subl $4, %0            \n\t"
  250.     "jnz 1b                \n\t"
  251.     :"+g"(h), "+S"(pixels), "+D"(block)
  252.     :"r" (line_size)
  253.     :"%eax", "memory");
  254. }
  255.  
  256. // Note this is not correctly rounded, but this function is only used for b frames so it doesnt matter 
  257. static void DEF(avg_pixels_xy2)(UINT8 *block, const UINT8 *pixels, int line_size, int h)
  258. {
  259.     MOVQ_BONE(mm6);
  260.     __asm __volatile(
  261.     "lea (%3, %3), %%eax        \n\t"
  262.     "movq (%1), %%mm0        \n\t"
  263.     PAVGB" 1(%1), %%mm0        \n\t"
  264.     ".balign 8            \n\t"
  265.     "1:                \n\t"
  266.     "movq (%1, %%eax), %%mm2    \n\t"
  267.     "movq (%1, %3), %%mm1        \n\t"
  268.     "psubusb %%mm6, %%mm2        \n\t"
  269.     PAVGB" 1(%1, %3), %%mm1        \n\t"
  270.     PAVGB" 1(%1, %%eax), %%mm2    \n\t"
  271.     "addl %%eax, %1            \n\t"
  272.     PAVGB" %%mm1, %%mm0        \n\t"
  273.     PAVGB" %%mm2, %%mm1        \n\t"
  274.     PAVGB" (%2), %%mm0        \n\t"
  275.     PAVGB" (%2, %3), %%mm1        \n\t"
  276.     "movq %%mm0, (%2)        \n\t"
  277.     "movq %%mm1, (%2, %3)        \n\t"
  278.     "movq (%1, %3), %%mm1        \n\t"
  279.     "movq (%1, %%eax), %%mm0    \n\t"
  280.     PAVGB" 1(%1, %3), %%mm1        \n\t"
  281.     PAVGB" 1(%1, %%eax), %%mm0    \n\t"
  282.     "addl %%eax, %2            \n\t"
  283.     "addl %%eax, %1            \n\t"
  284.     PAVGB" %%mm1, %%mm2        \n\t"
  285.     PAVGB" %%mm0, %%mm1        \n\t"
  286.     PAVGB" (%2), %%mm2        \n\t"
  287.     PAVGB" (%2, %3), %%mm1        \n\t"
  288.     "movq %%mm2, (%2)        \n\t"
  289.     "movq %%mm1, (%2, %3)        \n\t"
  290.     "addl %%eax, %2            \n\t"
  291.     "subl $4, %0            \n\t"
  292.     "jnz 1b                \n\t"
  293.     :"+g"(h), "+S"(pixels), "+D"(block)
  294.     :"r" (line_size)
  295.     :"%eax",  "memory");
  296. }
  297.