import of upstream 2.4.34.4 from kernel.org
[linux-2.4.git] / arch / alpha / lib / csum_ipv6_magic.S
1 /*
2  * arch/alpha/lib/csum_ipv6_magic.S
3  * Contributed by Richard Henderson <rth@tamu.edu>
4  *
5  * unsigned short csum_ipv6_magic(struct in6_addr *saddr,
6  *                                struct in6_addr *daddr,
7  *                                __u32 len,
8  *                                unsigned short proto,
9  *                                unsigned int csum);
10  */
11
12         .globl csum_ipv6_magic
13         .align 4
14         .ent csum_ipv6_magic
15         .frame $30,0,$26,0
16 csum_ipv6_magic:
17         .prologue 0
18
19         ldq     $0,0($16)       # e0    : load src & dst addr words
20         zapnot  $20,15,$20      # .. e1 : zero extend incoming csum
21         extqh   $18,1,$4        # e0    : byte swap len & proto while we wait
22         ldq     $1,8($16)       # .. e1 :
23
24         extbl   $18,1,$5        # e0    :
25         ldq     $2,0($17)       # .. e1 :
26         extbl   $18,2,$6        # e0    :
27         ldq     $3,8($17)       # .. e1 :
28
29         extbl   $18,3,$18       # e0    :
30         sra     $4,32,$4        # e0    :
31         sll     $5,16,$5        # e0    :
32         addq    $20,$0,$20      # .. e1 : begin summing the words
33
34         sll     $6,8,$6         # e0    :
35         cmpult  $20,$0,$0       # .. e1 :
36         extwh   $19,7,$7        # e0    :
37         or      $4,$18,$18      # .. e1 :
38
39         extbl   $19,1,$19       # e0    :
40         or      $5,$6,$5        # .. e1 :
41         or      $18,$5,$18      # e0    : len complete
42         or      $19,$7,$19      # .. e1 :
43
44         sll     $19,48,$19      # e0    :
45         addq    $20,$1,$20      # .. e1 :
46         sra     $19,32,$19      # e0    : proto complete
47         cmpult  $20,$1,$1       # .. e1 :
48
49         nop                     # e0    :
50         addq    $20,$2,$20      # .. e1 :
51         cmpult  $20,$2,$2       # e0    :
52         addq    $20,$3,$20      # .. e1 :
53
54         cmpult  $20,$3,$3       # e0    :
55         addq    $20,$18,$20     # .. e1 :
56         cmpult  $20,$18,$18     # e0    :
57         addq    $20,$19,$20     # .. e1 :
58
59         cmpult  $20,$19,$19     # e0    :
60         addq    $0,$1,$0        # .. e1 : merge the carries back into the csum
61         addq    $2,$3,$2        # e0    :
62         addq    $18,$19,$18     # .. e1 :
63
64         addq    $0,$2,$0        # e0    :
65         addq    $20,$18,$20     # .. e1 :
66         addq    $0,$20,$0       # e0    :
67         unop                    #       :
68
69         extwl   $0,2,$2         # e0    : begin folding the 64-bit value
70         zapnot  $0,3,$3         # .. e1 :
71         extwl   $0,4,$1         # e0    :
72         addq    $2,$3,$3        # .. e1 :
73
74         extwl   $0,6,$0         # e0    :
75         addq    $3,$1,$3        # .. e1 :
76         addq    $0,$3,$0        # e0    :
77         unop                    #       :
78
79         extwl   $0,2,$1         # e0    : fold 18-bit value
80         zapnot  $0,3,$0         # .. e1 :
81         addq    $0,$1,$0        # e0    :
82         unop                    #       :
83
84         extwl   $0,2,$1         # e0    : fold 17-bit value
85         zapnot  $0,3,$0         # .. e1 :
86         addq    $0,$1,$0        # e0    :
87         not     $0,$0           # e1    : and compliment.
88
89         zapnot  $0,3,$0         # e0    :
90         ret                     # .. e1 :
91
92         .end csum_ipv6_magic