asmb: more hax
[uebersetzerbau-ss10.git] / asmb / asmb.s
1         .file   "asmb.c"
2         .data
3         .align 16
4 const65:
5         .rept 16
6         .byte 0x65
7         .endr
8 const20:
9         .rept 16
10         .byte 0x20
11         .endr
12 constc0:
13         .rept 16
14         .byte 0xc0
15         .endr
16 const00:
17         .rept 16
18         .byte 0x00
19         .endr
20
21         .text
22 .globl asmb
23         .type   asmb, @function
24 asmb:
25 .LFB2:
26         //speicheradresse des parameters zurueckgeben
27         mov %rdi, %rax
28
29 .nextround:
30         //speicheradresse des pointers zeigt auf 16*8 feld = 128bit
31         movdqu (%rdi), %xmm11
32
33         // -64 - c
34         movdqa constc0, %xmm9
35         psubb %xmm11, %xmm9
36
37         // Packed COMpare Greater Than (Byte)"
38         // achtung beim intuitiven lesen des befehles. 'kleiner'
39         // ist mit 'groesser' vertauscht und vice versa
40         pcmpgtb const65, %xmm9
41
42 .differenz:
43         // Y = min(X, 'a' - 'A')
44         pand const20, %xmm9
45
46         // c += Y
47         paddb %xmm9, %xmm11
48
49         // retuniere an die richtige speicheradresse
50         movdqu %xmm11, (%rdi)
51
52         //entspricht ein byte dem nullbyte dann steht an jener stelle 0xff sonst 0x00
53         pcmpeqb const00, %xmm11
54         //hol die MSBs aller bytes raus
55         pmovmskb %xmm11, %ecx
56         add $16, %rdi
57
58         //ist %ecx gleich null? dann die naechsten 16byte bitte
59         jecxz .nextround
60
61 /*
62         //===============
63         //ab hier uebler hax um nach \0 trotzdem die gleichen bytes wie
64         //input zu haben, also um selbiges verhalten wie asmb_ref zu erzwingen
65
66         //\0 byte stelle durch rausfinden des MSB des %ecx
67         bsf %ecx, %r11d
68
69         //das ergebnis zweimal abspeichern
70         mov %r11d, %ecx
71
72         //hint: in %xmm9 ist differenz gespeichert (vgl .differenz)
73
74         //leider shiften nur mit immediate! :(
75         btr $3, %r11d
76         jnc .rechtsshift1
77         psrldq $8, %xmm9
78
79 .rechtsshift1:
80         btr $2, %r11d
81         jnc .rechtsshift2
82         psrldq $4, %xmm9
83
84 .rechtsshift2:
85         btr $1, %r11d
86         jnc .rechtsshift3
87         psrldq $2, %xmm9
88
89 .rechtsshift3:
90         btr $0, %r11d
91         jnc .linksshift
92         psrldq $1, %xmm9
93 #==================
94 .linksshift:
95         btr $3, %ecx
96         jnc .linksshift1
97         pslldq $8, %xmm9
98
99 .linksshift1:
100         btr $2, %ecx
101         jnc .linksshift2
102         pslldq $4, %xmm9
103
104 .linksshift2:
105         btr $1, %ecx
106         jnc .linksshift3
107         pslldq $2, %xmm9
108
109 .linksshift3:
110         btr $0, %ecx
111         jnc .endshift
112         pslldq $1, %xmm9
113
114 .endshift:
115         //betreffende speicherstelle in %xmm11 laden
116         movdqu -16(%rdi), %xmm11
117         //und overhead wieder subtrahieren
118         psubb %xmm9, %xmm11
119
120         //ergebnis zurueckspielen und fertig \o/
121         movdqu %xmm11, -16(%rdi)
122 */
123
124         ret
125 .LFE2:
126         .size   asmb, .-asmb
127         .section        .eh_frame,"a",@progbits
128 .Lframe1:
129         .long   .LECIE1-.LSCIE1
130 .LSCIE1:
131         .long   0x0
132         .byte   0x1
133         .string "zR"
134         .uleb128 0x1
135         .sleb128 -8
136         .byte   0x10
137         .uleb128 0x1
138         .byte   0x3
139         .byte   0xc
140         .uleb128 0x7
141         .uleb128 0x8
142         .byte   0x90
143         .uleb128 0x1
144         .align 8
145 .LECIE1:
146 .LSFDE1:
147         .long   .LEFDE1-.LASFDE1
148 .LASFDE1:
149         .long   .LASFDE1-.Lframe1
150         .long   .LFB2
151         .long   .LFE2-.LFB2
152         .uleb128 0x0
153         .align 8
154 .LEFDE1:
155         .ident  "GCC: (Debian 4.3.2-1.1) 4.3.2"
156         .section        .note.GNU-stack,"",@progbits