asma: hmm.. passt nu ned ganz?
[uebersetzerbau-ss10.git] / asma / asma.s
1         .file   "asma.c"
2         .text
3 .globl asma
4         .type   asma, @function
5 asma:
6 .LFB2:
7
8 /* unsigned char *asma(unsigned char *s)  
9 {  
10   int i;  
11   for (i=0; i<16; i++) {  
12     unsigned char c=s[i];  
13     c += (c>=’A’ && c<=’Z’) ? ’a’-’A’ : 0;  
14     s[i] = c;  
15   }  
16   return s;  
17 }
18
19 Schreiben Sie diese Funktion in Assembler unter Verwendung von pcmpgtb. Dabei ist folgende Äquivalenz hilfreich:
20 (c>=’A’ && c<=’Z’) ? ’a’-’A’ : 0;
21
22 ist (bei Verwendung von Überlauf-Arithmetik) äquivalent zu
23 min(’Z’+1+min_t-’A’ > c+min_t-’A’ ? 0xff : 0, ’a’-’A’)
24
25 wobei min_t der minimale Wert des Datentyps ist, den der Vergleich behandelt (bei pcmpgtb also -128). Zusätzlich zu dem oben genannten dürften die Befehle pminub, paddb, und psubb nützlich sein. */
26         pxor %xmm1, %xmm1
27         pxor %xmm2, %xmm2
28         pxor %xmm2, %xmm3
29         pxor %xmm2, %xmm4
30         pxor %xmm2, %xmm5
31
32         #init %xmm1 mit "'Z' + 1 + min_t - 'A'" fuer jedes byte
33         #'Z' + 1 + min_t - 'A' = 90 + 1 - 128 - 65 = -102
34         #102 = 01100110
35         #~102 = 10011001
36         #(~102)+1 = 10011010 = 0x9A
37         mov $0x9a9a9a9a9a9a9a9a, %rbx
38         movq %rbx, %xmm1
39         pslldq $8, %xmm1
40         movq %rbx, %xmm1
41
42         #init %xmm2 mit "'a'-'A'= 97-65 = 32 = 0x20
43         mov $0x2020202020202020, %rbx
44         movq %rbx, %xmm2
45         pslldq $8, %xmm2
46         movq %rbx, %xmm2
47
48         #speicheradresse des pointers zeigt auf 16*8 feld = 128bit
49         movdqu (%rdi), %xmm4
50         movdqu (%rdi), %xmm5
51
52         #addiere in %xmm4 "min_t-'A'"
53         # = -128 - 65 = 63 = 0x3f
54         mov $0x3f3f3f3f3f3f3f3f, %rbx
55         movq %rbx, %xmm3
56         pslldq $8, %xmm3
57         movq %rbx, %xmm3
58
59         #c+min_t-'A'
60         paddb %xmm3, %xmm4
61
62         #"Packed COMpare Greater Than (Byte)"
63         #bla = 'Z' + 1 + min_t - 'A' > c + min_t - 'A' ? 0xff : 0
64         #TODO: vllt vertauschen?
65         pcmpgtb %xmm4, %xmm1
66
67         #min(bla, 'a' - 'A')
68         pminub %xmm1, %xmm2
69
70         paddb %xmm2, %xmm5
71
72         movq %xmm5, (%rax)
73         ret
74 .LFE2:
75         .size   asma, .-asma
76         .section        .eh_frame,"a",@progbits
77 .Lframe1:
78         .long   .LECIE1-.LSCIE1
79 .LSCIE1:
80         .long   0x0
81         .byte   0x1
82         .string "zR"
83         .uleb128 0x1
84         .sleb128 -8
85         .byte   0x10
86         .uleb128 0x1
87         .byte   0x3
88         .byte   0xc
89         .uleb128 0x7
90         .uleb128 0x8
91         .byte   0x90
92         .uleb128 0x1
93         .align 8
94 .LECIE1:
95 .LSFDE1:
96         .long   .LEFDE1-.LASFDE1
97 .LASFDE1:
98         .long   .LASFDE1-.Lframe1
99         .long   .LFB2
100         .long   .LFE2-.LFB2
101         .uleb128 0x0
102         .align 8
103 .LEFDE1:
104         .ident  "GCC: (Debian 4.3.2-1.1) 4.3.2"
105         .section        .note.GNU-stack,"",@progbits