1// RUN: %Slang %s
2
3// RUN: %rs-filecheck-wrapper %s --check-prefix=CHECK-LL
4//     Check that the data types are properly padded:
5// CHECK-LL: %struct.NoBitfield{{(\.[0-9]+)?}} = type { i32, [4 x i8], i64, float, [4 x i8] }
6// CHECK-LL: %struct.Bitfield{{(\.[0-9]+)?}} = type { i32, [4 x i8], i64, i8 }
7//     Check that only NoBitfield is exported:
8// CHECK-LL: !\23rs_export_type = !{![[NODE:[0-9]+]]}
9// CHECK-LL: ![[NODE]] = !{!"NoBitfield"}
10
11// RUN: %scriptc-filecheck-wrapper --lang=Java --type=NoBitfield --check-prefix=CHECK-JAVA-STRUCT %s
12// CHECK-JAVA-STRUCT:      public static Element createElement(RenderScript rs) {
13// CHECK-JAVA-STRUCT-NEXT:     Element.Builder eb = new Element.Builder(rs);
14// CHECK-JAVA-STRUCT-NEXT:     eb.add(Element.I32(rs), "I");
15// CHECK-JAVA-STRUCT-NEXT:     eb.add(Element.U32(rs), "#rs_padding_1");
16// CHECK-JAVA-STRUCT-NEXT:     eb.add(Element.I64(rs), "L");
17// CHECK-JAVA-STRUCT-NEXT:     eb.add(Element.F32(rs), "F");
18// CHECK-JAVA-STRUCT-NEXT:     eb.add(Element.U32(rs), "#rs_padding_2");
19// CHECK-JAVA-STRUCT-NEXT:     return eb.create();
20// CHECK-JAVA-STRUCT-NEXT: }
21
22#pragma version(1)
23#pragma rs java_package_name(foo)
24
25// There is a C99 rule (under "Structure and union members") that
26// reads "One special guarantee is made in order to simplify the use
27// of unions: if a union contains several structures that share a
28// common initial sequence, and if the union object currently contains
29// one of these structures, it is permitted to inspect the common
30// initial part of any of them anywhere that a declaration of the
31// completed type of the union is visible. Two structures share a
32// common initial sequence if corresponding members have compatible
33// types (and, for bit-fields, the same widths) for a sequence of one
34// or more initial members."
35//
36// We want to ensure that the common initial sequences of exported
37// and non-exported types have the same layout.
38
39// An exported type (because we declare a global variable of this type)
40struct NoBitfield {
41    int I;
42    // expect 4 bytes of padding here
43    long L;
44    float F;
45    // expect 4 bytes of padding here
46};
47
48struct NoBitfield junk;  // just to make this an exported type
49
50// A non-exported type that shares a common initial sequence with NoBitfield
51struct Bitfield {
52    int I;
53    // expect 4 bytes of padding here
54    long L;
55    uint U:3;
56};
57
58union CommonInitialSequence {
59    struct NoBitfield nbf;
60    struct   Bitfield  bf;
61};
62
63static union CommonInitialSequence U, V;
64
65static struct NoBitfield *nbf;
66static struct   Bitfield * bf;
67
68// Note: Sets through the exported type (NoBitfield)
69void setUnion(long argL, int argI) {
70    nbf->L = argL;
71    nbf->I = argI;
72}
73
74bool failed = false;
75
76// Note: Tests through the non-exported type (Bitfield)
77void testUnion(long argL, int argI) {
78    failed |= ((bf->I != argI) || (bf->L != argL));
79}
80
81// Note: Prevent compiler from optimizing setUnion()/testUnion()
82//       to convert indirect accesses through nbf/bf into direct
83//       accesses through U or V.
84void choose(int i) {
85    if (i) {
86        nbf = &U.nbf;
87         bf = &U. bf;
88    } else {
89        nbf = &V.nbf;
90         bf = &V. bf;
91    }
92}
93