1a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham%verify "executed"
2a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham%verify "null object"
3a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham%verify "class cast exception thrown, with correct class name"
4a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham%verify "class cast exception not thrown on same class"
5a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham%verify "class cast exception not thrown on subclass"
6a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham%verify "class not resolved"
7a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham%verify "class already resolved"
8a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    /*
9a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham     * Check to see if a cast from one class to another is allowed.
10a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham     */
11a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    # check-cast vAA, class                /* BBBB */
12a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    GET_OPA(a3)                            #  a3 <- AA
13a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    FETCH(a2, 1)                           #  a2 <- BBBB
14a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    GET_VREG(rOBJ, a3)                     #  rOBJ <- object
15a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    LOAD_rSELF_methodClassDex(a0)          #  a0 <- pDvmDex
16a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    LOAD_base_offDvmDex_pResClasses(a0, a0) #  a0 <- pDvmDex->pResClasses
17a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    # is object null?
18a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    beqz      rOBJ, .L${opcode}_okay       #  null obj, cast always succeeds
19a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    LOAD_eas2(a1, a0, a2)                  #  a1 <- resolved class
20a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    LOAD_base_offObject_clazz(a0, rOBJ)    #  a0 <- obj->clazz
21a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    # have we resolved this before?
22a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    beqz      a1, .L${opcode}_resolve      #  not resolved, do it now
23a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham.L${opcode}_resolved:
24a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    # same class (trivial success)?
25a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    bne       a0, a1, .L${opcode}_fullcheck #  no, do full check
26a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham.L${opcode}_okay:
27a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    FETCH_ADVANCE_INST(2)                  #  advance rPC, load rINST
28a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    GET_INST_OPCODE(t0)                    #  extract opcode from rINST
29a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    GOTO_OPCODE(t0)                        #  jump to next instruction
30a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham
31a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    /*
32a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham     * Trivial test failed, need to perform full check.  This is common.
33a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham     *  a0 holds obj->clazz
34a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham     *  a1 holds class resolved from BBBB
35a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham     *  rOBJ holds object
36a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham     */
37a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham.L${opcode}_fullcheck:
38a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    move      rBIX,a1                      #  avoid ClassObject getting clobbered
39a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    JAL(dvmInstanceofNonTrivial)           #  v0 <- boolean result
40a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    # failed?
41a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    bnez      v0, .L${opcode}_okay         #  no, success
42a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    b         .L${opcode}_castfailure
43a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham%break
44a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham
45a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham.L${opcode}_castfailure:
46a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    # A cast has failed. We need to throw a ClassCastException with the
47a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    # class of the object that failed to be cast.
48a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    EXPORT_PC()                            #  about to throw
49a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    LOAD_base_offObject_clazz(a0, rOBJ)    #  a0 <- obj->clazz
50a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    move      a1,rBIX                      #  r1<- desired class
51a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    JAL(dvmThrowClassCastException)
52a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    b         common_exceptionThrown
53a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham
54a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    /*
55a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham     * Resolution required.  This is the least-likely path.
56a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham     *
57a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham     *  a2   holds BBBB
58a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham     *  rOBJ holds object
59a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham     */
60a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham.L${opcode}_resolve:
61a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    EXPORT_PC()                            #  resolve() could throw
62a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    LOAD_rSELF_method(a3)                  #  a3 <- self->method
63a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    move      a1, a2                       #  a1 <- BBBB
64a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    li        a2, 0                        #  a2 <- false
65a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    LOAD_base_offMethod_clazz(a0, a3)      #  a0 <- method->clazz
66a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    JAL(dvmResolveClass)                   #  v0 <- resolved ClassObject ptr
67a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    # got null?
68a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    beqz      v0, common_exceptionThrown   #  yes, handle exception
69a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    move      a1, v0                       #  a1 <- class resolved from BBB
70a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    LOAD_base_offObject_clazz(a0, rOBJ)    #  a0 <- obj->clazz
71a8b91c52fd8a90b784835dfe1f8898035266c4ddRaghu Gandham    b         .L${opcode}_resolved         #  pick up where we left off
72