1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149
|
// REQUIRED_ARGS: -preview=dip1021
/* Should compile successfully
*/
struct Allocation {
int* ptr;
size_t length;
}
void canFind(scope Allocation);
int* malloc();
void free(int*);
void pitcher();
void borrow(scope int*);
void borrow2c(const scope int*, const scope int*);
void out1(out int*);
/*****************************/
@live int* foo1(int* p)
{
return p; // consumes owner
}
@live int* foo2()
{
int* p = null;
return p; // consumes owner
}
@live int* foo3(int* p)
{
scope int* q = p; // borrows from p
return p; // use of p ends borrow in q
}
@live int* foo4(int* p)
{
scope int* bq = p; // borrow
scope const int* cq = p; // const borrow
return p; // ends both borrows
}
/*******************************/
@live void foo5()
{
auto p = malloc();
scope(exit) free(p);
pitcher();
}
/*******************************/
void deallocate(int* ptr, size_t length) @live
{
canFind(Allocation(ptr, length)); // canFind() borrows ptr
free(ptr);
}
/*******************************/
@live int* test1()
{
auto p = malloc();
scope b = p;
return p;
}
@live int* test2()
{
auto p = malloc();
auto q = p;
return q;
}
@live void test3()
{
auto p = malloc();
free(p);
}
@live void test4()
{
auto p = malloc();
borrow(p);
free(p);
}
@live void test5()
{
auto p = malloc();
scope q = p;
borrow2c(p, p);
free(p);
}
@live void test6()
{
int* p = void;
out1(p); // initialize
free(p); // consume
}
/*******************************/
void zoo1(int);
@live void zoo2() {
int* p = malloc();
zoo1(*p); // does not consume p
free(p);
}
@live void zoo3() {
int** p = cast(int**)malloc();
free(*p); // consumes p
}
@live void zoo4() {
int[] a = malloc()[0 .. 1];
zoo1(a[0]); // does not consume a
free(a.ptr); // consumes a
}
@live void zoo5() {
int*[] a = (cast(int**)malloc())[0 .. 1];
free(a[0]); // consumes a
}
struct S { int i; int* p; }
@live void zoo6() {
S* s = cast(S*)malloc();
zoo1(s.i); // does not consume s
free(cast(int*)s);
}
@live void zoo7() {
S* s = cast(S*)malloc();
free(s.p); // consumes s
}
|