Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 6 additions & 1 deletion spec/function.dd
Original file line number Diff line number Diff line change
Expand Up @@ -1241,8 +1241,13 @@ int foo(in int x, out int y, ref int z, int q);
$(TROW $(D scope), references in the parameter
cannot be escaped (e.g. assigned to a global variable).
Ignored for parameters with no references)
$(TROW $(D return), $(ARGS Parameter may be returned or copied to the first parameter,
but otherwise does not escape from the function.
Such copies are required not to outlive the argument(s) they were derived from.
Ignored for parameters with no references.
See $(DDSUBLINK spec/memory-safe-d, scope-return-params, Scope Parameters).))
$(TROW $(D lazy), argument is evaluated by the called function and not by the caller)
$(TROW $(D const), argument is implicitly converted to a const type)
$(TROW $(D const), argument is implicitly converted to a const type)
$(TROW $(D immutable), argument is implicitly converted to an immutable type)
$(TROW $(D shared), argument is implicitly converted to a shared type)
$(TROW $(D inout), argument is implicitly converted to an inout type)
Expand Down
49 changes: 41 additions & 8 deletions spec/memory-safe-d.dd
Original file line number Diff line number Diff line change
Expand Up @@ -24,19 +24,52 @@ $(HEADERNAV_TOC)

$(H2 $(LNAME2 usage, Usage))

$(P Memory safety can be enabled on a per-function basis using
the $(DDSUBLINK spec/function, safe-functions, $(D @safe) attribute).
This can be inferred when the compiler has the function body
available. The $(DDSUBLINK spec/function, trusted-functions, `@trusted` attribute) can be used when a function has a safe
interface, but uses unsafe code internally. These functions can
be called from $(D @safe) code.
$(P There are three categories of functions from the perspective of memory safety:)
$(UL
$(LI $(DDSUBLINK spec/function, safe-functions, `@safe`) functions)
$(LI $(DDSUBLINK spec/function, trusted-functions, `@trusted`) functions)
$(LI $(DDSUBLINK spec/function, system-functions, `@system`) functions)
)

$(P `@system` functions may perform any operation legal from the perspective of the language including inherently
memory unsafe operations like returning pointers to expired stackframes. These functions may not be called directly from
`@safe` functions.)

$(P `@trusted` functions have all the capabilities of `@system` functions but may be called from
`@safe` functions. For this reason they should be very limited in the scope of their use. Typical uses of
`@trusted` functions include wrapping system calls that take buffer pointer and length arguments separately so that
@safe` functions may call them with arrays.)

$(P `@safe` functions have a number of restrictions on what they may do and are intended to disallow operations that
may cause memory corruption. See $(DDSUBLINK spec/function, safe-functions, `@safe` functions).)

$(P These attributes may be inferred when the compiler has the function body available, such as with templates.)

$(P Array bounds checks are necessary to enforce memory safety, so
these are enabled (by default) for $(D @safe) code even in $(B
-release) mode.
these are enabled (by default) for `@safe` code even in $(B -release) mode.
)

$(H3 $(LNAME2 scope-return-params, Scope and Return Parameters))

$(P The function parameter attributes `return` and `scope` are used to track what happens to low-level pointers
passed to functions. Such pointers include: raw pointers, arrays, `this`, classes, `ref` parameters, delegate/lazy parameters,
and aggregates containing a pointer.)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Arrays? Or do you count those as aggregates?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggest we use raw pointers, this, variables of reference type, ref/lazy parameters, ref return values and aggregates containing such pointers.


$(P $(D scope) ensures that no references to the pointed-to object are retained, in global variables or pointers passed to the
function (and recursively to other functions called in the function), as a result of calling the function.
Variables in the function body and parameter list that are `scope` may have their allocations elided as a result.)

$(P $(D return) indicates that either the return value of the function or the first parameter is a pointer derived from the
`return` parameter or any other parameters also marked `return`.
For constructors, `return` applies to the (implicitly returned) `this` reference.
For void functions, `return` applies to the first parameter $(I iff) it is `ref`; this is to support UFCS,
property setters and non-member functions (e.g. `put` used like `put(dest, source)`).)

$(P These attributes may appear after the formal parameter list, in which case they apply either to a method's `this` parameter, or to
a free function's first parameter $(I iff) it is `ref`.
`return` or `scope` is ignored when applied to a type that is not a low-level pointer.)


$(H2 $(LNAME2 limitations, Limitations))

$(P Memory safety does not imply that code is portable, uses only
Expand Down