Subversion Repositories Kolibri OS

Rev

Go to most recent revision | Blame | Last modification | View Log | RSS feed

  1.  
  2. /*
  3.  * Mesa 3-D graphics library
  4.  *
  5.  * Copyright (C) 1999-2001  Brian Paul   All Rights Reserved.
  6.  *
  7.  * Permission is hereby granted, free of charge, to any person obtaining a
  8.  * copy of this software and associated documentation files (the "Software"),
  9.  * to deal in the Software without restriction, including without limitation
  10.  * the rights to use, copy, modify, merge, publish, distribute, sublicense,
  11.  * and/or sell copies of the Software, and to permit persons to whom the
  12.  * Software is furnished to do so, subject to the following conditions:
  13.  *
  14.  * The above copyright notice and this permission notice shall be included
  15.  * in all copies or substantial portions of the Software.
  16.  *
  17.  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
  18.  * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  19.  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
  20.  * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
  21.  * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
  22.  * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
  23.  * OTHER DEALINGS IN THE SOFTWARE.
  24.  */
  25.  
  26. /** TODO:
  27.   * - insert PREFETCH instructions to avoid cache-misses !
  28.   * - some more optimizations are possible...
  29.   * - for 40-50% more performance in the SSE-functions, the
  30.   *   data (trans-matrix, src_vert, dst_vert) needs to be 16byte aligned !
  31.   */
  32.  
  33. #ifdef USE_SSE_ASM
  34. #include "assyntax.h"
  35. #include "matypes.h"
  36. #include "xform_args.h"
  37.  
  38.    SEG_TEXT
  39.  
  40. #define S(i)    REGOFF(i * 4, ESI)
  41. #define D(i)    REGOFF(i * 4, EDI)
  42. #define M(i)    REGOFF(i * 4, EDX)
  43.  
  44.  
  45. ALIGNTEXT4
  46. GLOBL GLNAME(__mesa_sse_transform_points2_general)
  47. HIDDEN (__mesa_sse_transform_points2_general)
  48. GLNAME( __mesa_sse_transform_points2_general ):
  49.  
  50. #define FRAME_OFFSET 8
  51.     PUSH_L    ( ESI )
  52.     PUSH_L    ( EDI )
  53.  
  54.     MOV_L( REGOFF(OFFSET_SOURCE+8, ESP), ESI )  /* ptr to source GLvector4f */
  55.     MOV_L( REGOFF(OFFSET_DEST+8, ESP), EDI )    /* ptr to dest GLvector4f */
  56.  
  57.     MOV_L( ARG_MATRIX, EDX )                    /* ptr to matrix */
  58.     MOV_L( REGOFF(V4F_COUNT, ESI), ECX )        /* source count */
  59.  
  60.     TEST_L( ECX, ECX )
  61.     JZ( LLBL(K_GTP2GR_finish) )                 /* count was zero; go to finish */
  62.  
  63.     MOV_L( REGOFF(V4F_STRIDE, ESI), EAX )       /* stride */
  64.     OR_L( CONST(VEC_SIZE_4), REGOFF(V4F_FLAGS, EDI) )   /* set dest flags */
  65.  
  66.     MOV_L( ECX, REGOFF(V4F_COUNT, EDI) )        /* set dest count */
  67.     MOV_L( CONST(4), REGOFF(V4F_SIZE, EDI) )    /* set dest size */
  68.  
  69.     SHL_L( CONST(4), ECX )                      /* count *= 16 */
  70.     MOV_L( REGOFF(V4F_START, ESI), ESI )        /* ptr to first source vertex */
  71.  
  72.     MOV_L( REGOFF(V4F_START, EDI), EDI )        /* ptr to first dest vertex */
  73.     ADD_L( EDI, ECX )                           /* count += dest ptr */
  74.  
  75. ALIGNTEXT32
  76.     MOVAPS( M(0), XMM0 )                        /* m3  | m2  | m1  | m0 */
  77.     MOVAPS( M(4), XMM1 )                        /* m7  | m6  | m5  | m4 */
  78.     MOVAPS( M(12), XMM2 )                       /* m15 | m14 | m13 | m12 */
  79.  
  80. ALIGNTEXT32
  81. LLBL(K_GTP2GR_top):
  82.     MOVSS( S(0), XMM3 )                         /* ox */
  83.     SHUFPS( CONST(0x0), XMM3, XMM3 )            /* ox | ox | ox | ox */
  84.     MULPS( XMM0, XMM3 )                         /* ox*m3 | ox*m2 | ox*m1 | ox*m0 */
  85.     MOVSS( S(1), XMM4 )                         /* oy */
  86.     SHUFPS( CONST(0x0), XMM4, XMM4 )            /* oy | oy | oy | oy */
  87.     MULPS( XMM1, XMM4 )                         /* oy*m7 | oy*m6 | oy*m5 | oy*m4 */
  88.  
  89.     ADDPS( XMM4, XMM3 )
  90.     ADDPS( XMM2, XMM3 )
  91.     MOVAPS( XMM3, D(0) )
  92.  
  93. LLBL(K_GTP2GR_skip):
  94.     ADD_L     ( CONST(16), EDI )
  95.     ADD_L     ( EAX, ESI )
  96.     CMP_L     ( ECX, EDI )
  97.     JNE       ( LLBL(K_GTP2GR_top) )
  98.  
  99. LLBL(K_GTP2GR_finish):
  100.     POP_L     ( EDI )
  101.     POP_L     ( ESI )
  102.     RET
  103. #undef FRAME_OFFSET
  104.  
  105.  
  106. ALIGNTEXT4
  107. GLOBL GLNAME(__mesa_sse_transform_points2_identity)
  108. HIDDEN(__mesa_sse_transform_points2_identity)
  109. GLNAME( __mesa_sse_transform_points2_identity ):
  110.  
  111. #define FRAME_OFFSET 8
  112.     PUSH_L    ( ESI )
  113.     PUSH_L    ( EDI )
  114.  
  115.     MOV_L( REGOFF(OFFSET_SOURCE+8, ESP), ESI ) /* ptr to source GLvector4f */
  116.     MOV_L( REGOFF(OFFSET_DEST+8, ESP), EDI )    /* ptr to dest GLvector4f */
  117.  
  118.     MOV_L( REGOFF(V4F_COUNT, ESI), ECX )        /* source count */
  119.  
  120.     TEST_L( ECX, ECX)
  121.     JZ( LLBL(K_GTP2IR_finish) )                 /* count was zero; go to finish */
  122.  
  123.     MOV_L( REGOFF(V4F_STRIDE, ESI), EAX )       /* stride */
  124.     OR_L( CONST(VEC_SIZE_2), REGOFF(V4F_FLAGS, EDI) )   /* set dest flags */
  125.  
  126.     MOV_L( ECX, REGOFF(V4F_COUNT, EDI) )        /* set dest count */
  127.     MOV_L( CONST(2), REGOFF(V4F_SIZE, EDI) )    /* set dest size */
  128.  
  129.     SHL_L( CONST(4), ECX )                      /* count *= 16 */
  130.     MOV_L( REGOFF(V4F_START, ESI), ESI )        /* ptr to first source vertex */
  131.  
  132.     MOV_L( REGOFF(V4F_START, EDI), EDI )        /* ptr to first dest vertex */
  133.     ADD_L( EDI, ECX )                           /* count += dest ptr */
  134.  
  135.     CMP_L( ESI, EDI )
  136.     JE( LLBL(K_GTP2IR_finish) )
  137.  
  138.  
  139. ALIGNTEXT32
  140. LLBL(K_GTP2IR_top):
  141.     MOV_L     ( S(0), EDX )
  142.     MOV_L     ( EDX, D(0) )
  143.     MOV_L     ( S(1), EDX )
  144.     MOV_L     ( EDX, D(1) )
  145.  
  146. LLBL(K_GTP2IR_skip):
  147.     ADD_L     ( CONST(16), EDI )
  148.     ADD_L     ( EAX, ESI )
  149.     CMP_L     ( ECX, EDI )
  150.     JNE       ( LLBL(K_GTP2IR_top) )
  151.  
  152. LLBL(K_GTP2IR_finish):
  153.     POP_L     ( EDI )
  154.     POP_L     ( ESI )
  155.     RET
  156. #undef FRAME_OFFSET
  157.  
  158.  
  159. ALIGNTEXT4
  160. GLOBL GLNAME(__mesa_sse_transform_points2_3d_no_rot)
  161. HIDDEN(__mesa_sse_transform_points2_3d_no_rot)
  162. GLNAME(__mesa_sse_transform_points2_3d_no_rot):
  163.  
  164. #define FRAME_OFFSET 8
  165.     PUSH_L( ESI )
  166.     PUSH_L( EDI )
  167.  
  168.     MOV_L( REGOFF(OFFSET_SOURCE+8, ESP), ESI )  /* ptr to source GLvector4f */
  169.     MOV_L( REGOFF(OFFSET_DEST+8, ESP), EDI )    /* ptr to dest GLvector4f */
  170.  
  171.     MOV_L( ARG_MATRIX, EDX )                    /* ptr to matrix */
  172.     MOV_L( REGOFF(V4F_COUNT, ESI), ECX )        /* source count */
  173.  
  174.     TEST_L( ECX, ECX)
  175.     JZ( LLBL(K_GTP23DNRR_finish) )              /* count was zero; go to finish */
  176.  
  177.     MOV_L( REGOFF(V4F_STRIDE, ESI), EAX )       /* stride */
  178.     OR_L( CONST(VEC_SIZE_3), REGOFF(V4F_FLAGS, EDI) )   /* set dest flags */
  179.  
  180.     MOV_L( ECX, REGOFF(V4F_COUNT, EDI) )        /* set dest count */
  181.     MOV_L( CONST(3), REGOFF(V4F_SIZE, EDI) )    /* set dest size */
  182.  
  183.     SHL_L( CONST(4), ECX )                      /* count *= 16 */
  184.     MOV_L( REGOFF(V4F_START, ESI), ESI )        /* ptr to first source vertex */
  185.  
  186.     MOV_L( REGOFF(V4F_START, EDI), EDI )        /* ptr to first dest vertex */
  187.     ADD_L( EDI, ECX )                           /* count += dest ptr */
  188.  
  189.     XORPS( XMM0, XMM0 )                         /* clean the working register */
  190.  
  191. ALIGNTEXT32
  192.     MOVSS    ( M(0), XMM1 )                     /* - | - |  -  | m0  */
  193.     MOVSS    ( M(5), XMM2 )                     /* - | - |  -  | m5  */
  194.     UNPCKLPS ( XMM2, XMM1 )                     /* - | - | m5  | m0  */
  195.     MOVLPS   ( M(12), XMM2 )                    /* - | - | m13 | m12 */
  196.     MOVSS    ( M(14), XMM3 )                    /* - | - |  -  | m14 */
  197.  
  198. ALIGNTEXT32
  199. LLBL(K_GTP23DNRR_top):
  200.     MOVLPS   ( S(0), XMM0 )                     /* - | - |  oy   | ox */
  201.     MULPS    ( XMM1, XMM0 )                     /* - | - | oy*m5 | ox*m0 */
  202.     ADDPS    ( XMM2, XMM0 )                     /* - | - | +m13  | +m12 */
  203.     MOVLPS   ( XMM0, D(0) )                     /* -> D(1) | -> D(0) */
  204.  
  205.     MOVSS    ( XMM3, D(2) )                     /* -> D(2) */
  206.  
  207. LLBL(K_GTP23DNRR_skip):
  208.     ADD_L    ( CONST(16), EDI )
  209.     ADD_L    ( EAX, ESI )
  210.     CMP_L    ( ECX, EDI )
  211.     JNE      ( LLBL(K_GTP23DNRR_top) )
  212.  
  213. LLBL(K_GTP23DNRR_finish):
  214.     POP_L    ( EDI )
  215.     POP_L    ( ESI )
  216.     RET
  217. #undef FRAME_OFFSET
  218.  
  219.  
  220. ALIGNTEXT4
  221. GLOBL GLNAME(__mesa_sse_transform_points2_perspective)
  222. HIDDEN(__mesa_sse_transform_points2_perspective)
  223. GLNAME(__mesa_sse_transform_points2_perspective):
  224.  
  225. #define FRAME_OFFSET 8
  226.     PUSH_L   ( ESI )
  227.     PUSH_L   ( EDI )
  228.  
  229.     MOV_L( REGOFF(OFFSET_SOURCE+8, ESP), ESI )  /* ptr to source GLvector4f */
  230.     MOV_L( REGOFF(OFFSET_DEST+8, ESP), EDI )    /* ptr to dest GLvector4f */
  231.  
  232.     MOV_L( ARG_MATRIX, EDX )                    /* ptr to matrix */
  233.     MOV_L( REGOFF(V4F_COUNT, ESI), ECX )        /* source count */
  234.  
  235.     TEST_L( ECX, ECX)
  236.     JZ( LLBL(K_GTP23PR_finish) )                /* count was zero; go to finish */
  237.  
  238.     MOV_L( REGOFF(V4F_STRIDE, ESI), EAX )       /* stride */
  239.     OR_L( CONST(VEC_SIZE_4), REGOFF(V4F_FLAGS, EDI) )   /* set dest flags */
  240.  
  241.     MOV_L( ECX, REGOFF(V4F_COUNT, EDI) )        /* set dest count */
  242.     MOV_L( CONST(4), REGOFF(V4F_SIZE, EDI) )    /* set dest size */
  243.  
  244.     SHL_L( CONST(4), ECX )                      /* count *= 16 */
  245.     MOV_L( REGOFF(V4F_START, ESI), ESI )        /* ptr to first source vertex */
  246.  
  247.     MOV_L( REGOFF(V4F_START, EDI), EDI )        /* ptr to first dest vertex */
  248.     ADD_L( EDI, ECX )                           /* count += dest ptr */
  249.  
  250. ALIGNTEXT32
  251.     MOVSS    ( M(0), XMM1 )                     /* -  | -  |  -  | m0  */
  252.     MOVSS    ( M(5), XMM2 )                     /* -  | -  |  -  | m5  */
  253.     UNPCKLPS ( XMM2, XMM1 )                     /* -  | -  | m5  | m0  */
  254.     MOVSS    ( M(14), XMM3 )                    /* m14 */
  255.     XORPS    ( XMM0, XMM0 )                     /* 0 | 0 | 0 | 0 */
  256.  
  257. ALIGNTEXT32
  258. LLBL(K_GTP23PR_top):
  259.     MOVLPS( S(0), XMM4 )                        /* oy | ox */
  260.     MULPS( XMM1, XMM4 )                         /* oy*m5 | ox*m0 */
  261.     MOVLPS( XMM4, D(0) )                        /* ->D(1) | ->D(0) */
  262.     MOVSS( XMM3, D(2) )                         /* ->D(2) */
  263.     MOVSS( XMM0, D(3) )                         /* ->D(3) */
  264.  
  265. LLBL(K_GTP23PR_skip):
  266.     ADD_L( CONST(16), EDI )
  267.     ADD_L( EAX, ESI )
  268.     CMP_L( ECX, EDI )
  269.     JNE( LLBL(K_GTP23PR_top) )
  270.  
  271. LLBL(K_GTP23PR_finish):
  272.     POP_L    ( EDI )
  273.     POP_L    ( ESI )
  274.     RET
  275. #undef FRAME_OFFSET
  276.  
  277.  
  278.  
  279. ALIGNTEXT4
  280. GLOBL GLNAME(__mesa_sse_transform_points2_2d)
  281. HIDDEN(__mesa_sse_transform_points2_2d)
  282. GLNAME(__mesa_sse_transform_points2_2d):
  283.  
  284. #define FRAME_OFFSET 8
  285.     PUSH_L( ESI )
  286.     PUSH_L( EDI )
  287.  
  288.     MOV_L( REGOFF(OFFSET_SOURCE+8, ESP), ESI )  /* ptr to source GLvector4f */
  289.     MOV_L( REGOFF(OFFSET_DEST+8, ESP), EDI )    /* ptr to dest GLvector4f */
  290.  
  291.     MOV_L( ARG_MATRIX, EDX )                    /* ptr to matrix */
  292.     MOV_L( REGOFF(V4F_COUNT, ESI), ECX )        /* source count */
  293.  
  294.     TEST_L( ECX, ECX)
  295.     JZ( LLBL(K_GTP23P2DR_finish) )              /* count was zero; go to finish */
  296.  
  297.     MOV_L( REGOFF(V4F_STRIDE, ESI), EAX )       /* stride */
  298.     OR_L( CONST(VEC_SIZE_2), REGOFF(V4F_FLAGS, EDI) )   /* set dest flags */
  299.  
  300.     MOV_L( ECX, REGOFF(V4F_COUNT, EDI) )        /* set dest count */
  301.     MOV_L( CONST(2), REGOFF(V4F_SIZE, EDI) )    /* set dest size */
  302.  
  303.     SHL_L( CONST(4), ECX )                      /* count *= 16 */
  304.     MOV_L( REGOFF(V4F_START, ESI), ESI )        /* ptr to first source vertex */
  305.  
  306.     MOV_L( REGOFF(V4F_START, EDI), EDI )        /* ptr to first dest vertex */
  307.     ADD_L( EDI, ECX )                           /* count += dest ptr */
  308.  
  309. ALIGNTEXT32
  310.     MOVLPS( M(0), XMM0 )                        /* m1  | m0 */
  311.     MOVLPS( M(4), XMM1 )                        /* m5  | m4 */
  312.     MOVLPS( M(12), XMM2 )                       /* m13 | m12 */
  313.  
  314. ALIGNTEXT32
  315. LLBL(K_GTP23P2DR_top):
  316.     MOVSS( S(0), XMM3 )                         /* ox */
  317.     SHUFPS( CONST(0x0), XMM3, XMM3 )            /* ox | ox */
  318.     MULPS( XMM0, XMM3 )                         /* ox*m1 | ox*m0 */
  319.  
  320.     MOVSS( S(1), XMM4 )                         /* oy */
  321.     SHUFPS( CONST(0x0), XMM4, XMM4 )            /* oy | oy */
  322.     MULPS( XMM1, XMM4 )                         /* oy*m5 | oy*m4 */
  323.  
  324.     ADDPS( XMM4, XMM3 )
  325.     ADDPS( XMM2, XMM3 )
  326.     MOVLPS( XMM3, D(0) )                        /* ->D(1) | ->D(0) */
  327.  
  328. LLBL(K_GTP23P2DR_skip):
  329.     ADD_L    ( CONST(16), EDI )
  330.     ADD_L    ( EAX, ESI )
  331.     CMP_L    ( ECX, EDI )
  332.     JNE      ( LLBL(K_GTP23P2DR_top) )
  333.  
  334. LLBL(K_GTP23P2DR_finish):
  335.     POP_L    ( EDI )
  336.     POP_L    ( ESI )
  337.     RET
  338. #undef FRAME_OFFSET
  339.  
  340.  
  341.  
  342. ALIGNTEXT4
  343. GLOBL GLNAME(__mesa_sse_transform_points2_2d_no_rot)
  344. HIDDEN(__mesa_sse_transform_points2_2d_no_rot)
  345. GLNAME(__mesa_sse_transform_points2_2d_no_rot):
  346.  
  347. #define FRAME_OFFSET 8
  348.         PUSH_L( ESI )
  349.         PUSH_L( EDI )
  350.  
  351.         MOV_L( REGOFF(OFFSET_SOURCE+8, ESP), ESI )      /* ptr to source GLvector4f */
  352.         MOV_L( REGOFF(OFFSET_DEST+8, ESP), EDI )        /* ptr to dest GLvector4f */
  353.  
  354.         MOV_L( ARG_MATRIX, EDX )                /* ptr to matrix */
  355.         MOV_L( REGOFF(V4F_COUNT, ESI), ECX )    /* source count */
  356.  
  357.         TEST_L( ECX, ECX)
  358.         JZ( LLBL(K_GTP23P2DNRR_finish) )        /* count was zero; go to finish */
  359.  
  360.         MOV_L( REGOFF(V4F_STRIDE, ESI), EAX )   /* stride */
  361.         OR_L( CONST(VEC_SIZE_2), REGOFF(V4F_FLAGS, EDI) )       /* set dest flags */
  362.  
  363.         MOV_L( ECX, REGOFF(V4F_COUNT, EDI) )    /* set dest count */
  364.         MOV_L( CONST(2), REGOFF(V4F_SIZE, EDI) )        /* set dest size */
  365.  
  366.         SHL_L( CONST(4), ECX )                  /* count *= 16 */
  367.         MOV_L( REGOFF(V4F_START, ESI), ESI )    /* ptr to first source vertex */
  368.  
  369.         MOV_L( REGOFF(V4F_START, EDI), EDI )    /* ptr to first dest vertex */
  370.         ADD_L( EDI, ECX )                       /* count += dest ptr */
  371.  
  372. ALIGNTEXT32
  373.         MOVSS    ( M(0), XMM1 )                 /* m0 */
  374.         MOVSS    ( M(5), XMM2 )                 /* m5 */
  375.         UNPCKLPS ( XMM2, XMM1 )                 /* m5 | m0 */
  376.         MOVLPS   ( M(12), XMM2 )                /* m13 | m12 */
  377.  
  378. ALIGNTEXT32
  379. LLBL(K_GTP23P2DNRR_top):
  380.         MOVLPS( S(0), XMM0 )                    /* oy | ox */
  381.         MULPS( XMM1, XMM0 )                     /* oy*m5 | ox*m0 */
  382.         ADDPS( XMM2, XMM0 )                     /* +m13 | +m12 */
  383.         MOVLPS( XMM0, D(0) )                    /* ->D(1) | ->D(0) */
  384.  
  385. LLBL(K_GTP23P2DNRR_skip):
  386.         ADD_L( CONST(16), EDI )
  387.         ADD_L( EAX, ESI )
  388.         CMP_L( ECX, EDI )
  389.         JNE( LLBL(K_GTP23P2DNRR_top) )
  390.  
  391. LLBL(K_GTP23P2DNRR_finish):
  392.         POP_L( EDI )
  393.         POP_L( ESI )
  394.         RET
  395. #undef FRAME_OFFSET
  396.  
  397.  
  398.  
  399. ALIGNTEXT4
  400. GLOBL GLNAME(__mesa_sse_transform_points2_3d)
  401. HIDDEN(__mesa_sse_transform_points2_3d)
  402. GLNAME(__mesa_sse_transform_points2_3d):
  403.  
  404. #define FRAME_OFFSET 8
  405.         PUSH_L( ESI )
  406.         PUSH_L( EDI )
  407.  
  408.         MOV_L( REGOFF(OFFSET_SOURCE+8, ESP), ESI )      /* ptr to source GLvector4f */
  409.         MOV_L( REGOFF(OFFSET_DEST+8, ESP), EDI )        /* ptr to dest GLvector4f */
  410.  
  411.         MOV_L( ARG_MATRIX, EDX )                /* ptr to matrix */
  412.         MOV_L( REGOFF(V4F_COUNT, ESI), ECX )    /* source count */
  413.  
  414.         TEST_L( ECX, ECX)
  415.         JZ( LLBL(K_GTP23P3DR_finish) )  /* count was zero; go to finish */
  416.  
  417.         MOV_L( REGOFF(V4F_STRIDE, ESI), EAX )   /* stride */
  418.         OR_L( CONST(VEC_SIZE_3), REGOFF(V4F_FLAGS, EDI) )       /* set dest flags */
  419.  
  420.         MOV_L( ECX, REGOFF(V4F_COUNT, EDI) )    /* set dest count */
  421.         MOV_L( CONST(3), REGOFF(V4F_SIZE, EDI) )        /* set dest size */
  422.  
  423.         SHL_L( CONST(4), ECX )                  /* count *= 16 */
  424.         MOV_L( REGOFF(V4F_START, ESI), ESI )    /* ptr to first source vertex */
  425.  
  426.         MOV_L( REGOFF(V4F_START, EDI), EDI )    /* ptr to first dest vertex */
  427.         ADD_L( EDI, ECX )                       /* count += dest ptr */
  428.  
  429. ALIGNTEXT32
  430.         MOVAPS( M(0), XMM0 )                    /* m2  | m1  | m0 */
  431.         MOVAPS( M(4), XMM1 )                    /* m6  | m5  | m4 */
  432.         MOVAPS( M(12), XMM2 )                   /* m14 | m13 | m12 */
  433.  
  434. ALIGNTEXT32
  435. LLBL(K_GTP23P3DR_top):
  436.         MOVSS( S(0), XMM3 )                     /* ox */
  437.         SHUFPS( CONST(0x0), XMM3, XMM3 )        /* ox | ox | ox */
  438.         MULPS( XMM0, XMM3 )                     /* ox*m2 | ox*m1 | ox*m0 */
  439.  
  440.         MOVSS( S(1), XMM4 )                     /* oy */
  441.         SHUFPS( CONST(0x0), XMM4, XMM4 )        /* oy | oy | oy */
  442.         MULPS( XMM1, XMM4 )                     /* oy*m6 | oy*m5 | oy*m4 */
  443.  
  444.         ADDPS( XMM4, XMM3 )
  445.         ADDPS( XMM2, XMM3 )
  446.  
  447.         MOVLPS( XMM3, D(0) )                    /* ->D(1) | ->D(0) */
  448.         UNPCKHPS( XMM3, XMM3 )
  449.         MOVSS( XMM3, D(2) )                     /* ->D(2) */
  450.  
  451. LLBL(K_GTP23P3DR_skip):
  452.         ADD_L( CONST(16), EDI )
  453.         ADD_L( EAX, ESI )
  454.         CMP_L( ECX, EDI )
  455.         JNE( LLBL(K_GTP23P3DR_top) )
  456.  
  457. LLBL(K_GTP23P3DR_finish):
  458.         POP_L( EDI )
  459.         POP_L( ESI )
  460.         RET
  461. #undef FRAME_OFFSET
  462. #endif
  463.  
  464. #if defined (__ELF__) && defined (__linux__)
  465.         .section .note.GNU-stack,"",%progbits
  466. #endif
  467.