1fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    /*
2fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     * String's compareTo.
3fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     *
4fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     * Requires r0/r1 to have been previously checked for null.  Will
5fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     * return negative if this's string is < comp, 0 if they are the
6fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     * same and positive if >.
7fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     *
8fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     * IMPORTANT NOTE:
9fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     *
10fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     * This code relies on hard-coded offsets for string objects, and must be
11fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     * kept in sync with definitions in UtfString.h.  See asm-constants.h
12fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     *
13fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     * On entry:
14fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     *    r0:   this object pointer
15fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     *    r1:   comp object pointer
16fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     *
17fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     */
18fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee
19fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    mov    r2, r0         @ this to r2, opening up r0 for return value
20fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    subs   r0, r2, r1     @ Same?
21fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    bxeq   lr
22fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee
23fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    ldr    r4, [r2, #STRING_FIELDOFF_OFFSET]
24fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    ldr    r9, [r1, #STRING_FIELDOFF_OFFSET]
25fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    ldr    r7, [r2, #STRING_FIELDOFF_COUNT]
26fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    ldr    r10, [r1, #STRING_FIELDOFF_COUNT]
27fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    ldr    r2, [r2, #STRING_FIELDOFF_VALUE]
28fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    ldr    r1, [r1, #STRING_FIELDOFF_VALUE]
29fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee
30fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    /*
31fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     * At this point, we have:
32fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     *    value:  r2/r1
33fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     *    offset: r4/r9
34fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     *    count:  r7/r10
35fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     * We're going to compute
36fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     *    r11 <- countDiff
37fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     *    r10 <- minCount
38fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     */
39fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     subs  r11, r7, r10
40fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     movls r10, r7
41fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee
42fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     /* Now, build pointers to the string data */
43fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     add   r2, r2, r4, lsl #1
44fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     add   r1, r1, r9, lsl #1
45fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     /*
46fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee      * Note: data pointers point to previous element so we can use pre-index
47fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee      * mode with base writeback.
48fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee      */
49fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     add   r2, #16-2   @ offset to contents[-1]
50fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     add   r1, #16-2   @ offset to contents[-1]
51fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee
52fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee     /*
53fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee      * At this point we have:
54fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee      *   r2: *this string data
55fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee      *   r1: *comp string data
56fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee      *   r10: iteration count for comparison
57fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee      *   r11: value to return if the first part of the string is equal
58fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee      *   r0: reserved for result
59fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee      *   r3, r4, r7, r8, r9, r12 available for loading string data
60fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee      */
61fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee
624c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    subs  r10, #2
634c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    blt   do_remainder2
644c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee
654c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee      /*
664c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee       * Unroll the first two checks so we can quickly catch early mismatch
674c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee       * on long strings (but preserve incoming alignment)
684c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee       */
694c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee
704c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    ldrh  r3, [r2, #2]!
714c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    ldrh  r4, [r1, #2]!
724c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    ldrh  r7, [r2, #2]!
734c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    ldrh  r8, [r1, #2]!
744c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    subs  r0, r3, r4
754c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    subeqs  r0, r7, r8
764c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    bxne  lr
774c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    cmp   r10, #28
784c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    bgt   do_memcmp16
794c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    subs  r10, #3
80fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    blt   do_remainder
814c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee
82fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbeeloopback_triple:
83fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    ldrh  r3, [r2, #2]!
84fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    ldrh  r4, [r1, #2]!
85fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    ldrh  r7, [r2, #2]!
86fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    ldrh  r8, [r1, #2]!
87fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    ldrh  r9, [r2, #2]!
88fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    ldrh  r12,[r1, #2]!
89fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    subs  r0, r3, r4
90fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    subeqs  r0, r7, r8
91fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    subeqs  r0, r9, r12
92fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    bxne  lr
93fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    subs  r10, #3
945965d47b624798343b6a53afd384f2cf88d091deBill Buzbee    bge   loopback_triple
95fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee
96fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbeedo_remainder:
975965d47b624798343b6a53afd384f2cf88d091deBill Buzbee    adds  r10, #3
98fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    beq   returnDiff
99fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee
100fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbeeloopback_single:
101fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    ldrh  r3, [r2, #2]!
102fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    ldrh  r4, [r1, #2]!
103fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    subs  r0, r3, r4
104fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    bxne  lr
105fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    subs  r10, #1
106fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    bne     loopback_single
107fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee
108fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill BuzbeereturnDiff:
109fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    mov   r0, r11
110fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee    bx    lr
111fd023aaec5f2b0df61d1702ea2f29a70abe90158Bill Buzbee
1124c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbeedo_remainder2:
1134c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    adds  r10, #2
1144c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    bne   loopback_single
1154c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    mov   r0, r11
1164c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    bx    lr
1174c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee
1184c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    /* Long string case */
1194c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbeedo_memcmp16:
1204c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    mov   r4, lr
1214c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    ldr   lr, .Lmemcmp16
1224c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    mov   r7, r11
1234c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    add   r0, r2, #2
1244c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    add   r1, r1, #2
1254c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    mov   r2, r10
1264c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    blx   lr
1274c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    cmp   r0, #0
1284c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    bxne  r4
1294c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    mov   r0, r7
1304c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    bx    r4
1314c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee
1324c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee.Lmemcmp16:
1334c0dedfd9006daee4f6d96482cc6ac94a1797880Bill Buzbee    .word __memcmp16
134