about summary refs log tree commit diff
path: root/src
diff options
context:
space:
mode:
authorJorge Aparicio <japaricious@gmail.com>2017-04-06 00:04:33 -0500
committerJorge Aparicio <japaricious@gmail.com>2017-04-06 00:04:33 -0500
commit763beff5d1bcfb74d2930decd731a43a7d3ad080 (patch)
tree1937bdf240db551802876bd69a788ec28e4dbf65 /src
parentbbe54115873eca9d9a889be3d9eff0c01d2ba8be (diff)
downloadrust-763beff5d1bcfb74d2930decd731a43a7d3ad080.tar.gz
rust-763beff5d1bcfb74d2930decd731a43a7d3ad080.zip
add documentation to the unstable book
Diffstat (limited to 'src')
-rw-r--r--src/doc/unstable-book/src/SUMMARY.md1
-rw-r--r--src/doc/unstable-book/src/used.md152
2 files changed, 153 insertions, 0 deletions
diff --git a/src/doc/unstable-book/src/SUMMARY.md b/src/doc/unstable-book/src/SUMMARY.md
index 292f5a1ec81..0459c6a2519 100644
--- a/src/doc/unstable-book/src/SUMMARY.md
+++ b/src/doc/unstable-book/src/SUMMARY.md
@@ -203,6 +203,7 @@
 - [unwind_attributes](unwind-attributes.md)
 - [update_panic_count](update-panic-count.md)
 - [use_extern_macros](use-extern-macros.md)
+- [used](used.md)
 - [utf8_error_error_len](utf8-error-error-len.md)
 - [vec_remove_item](vec-remove-item.md)
 - [windows_c](windows-c.md)
diff --git a/src/doc/unstable-book/src/used.md b/src/doc/unstable-book/src/used.md
new file mode 100644
index 00000000000..749c9a8ec28
--- /dev/null
+++ b/src/doc/unstable-book/src/used.md
@@ -0,0 +1,152 @@
+# `used`
+
+The tracking issue for this feature is: 40289.
+
+------------------------
+
+The `#[used]` attribute can be applied to `static` variables to prevent the Rust
+compiler from optimizing them away even if they appear to be unused by the crate
+(appear to be "dead code").
+
+``` rust
+#![feature(used)]
+
+#[used]
+static FOO: i32 = 1;
+
+static BAR: i32 = 2;
+
+fn main() {}
+```
+
+If you compile this program into an object file, you'll see that `FOO` makes it
+to the object file but `BAR` doesn't. Neither static variable is used by the
+program.
+
+``` text
+$ rustc -C opt-level=3 --emit=obj used.rs
+
+$ nm -C used.o
+0000000000000000 T main
+                 U std::rt::lang_start
+0000000000000000 r used::FOO
+0000000000000000 t used::main
+```
+
+Note that the *linker* knows nothing about the `#[used]` attribute and will
+remove `#[used]` symbols if they are not referenced by other parts of the
+program:
+
+``` text
+$ rustc -C opt-level=3 used.rs
+
+$ nm -C used | grep FOO
+```
+
+"This doesn't sound too useful then!" you may think but keep reading.
+
+To preserve the symbols all the way to the final binary, you'll need the
+cooperation of the linker. Here's one example:
+
+The ELF standard defines two special sections, `.init_array` and
+`.pre_init_array`, that may contain function pointers which will be executed
+*before* the `main` function is invoked. The linker will preserve symbols placed
+in these sections (at least when linking programs that target the `*-*-linux-*`
+targets).
+
+``` rust
+#![feature(used)]
+
+extern "C" fn before_main() {
+    println!("Hello, world!");
+}
+
+#[link_section = ".init_array"]
+#[used]
+static INIT_ARRAY: [extern "C" fn(); 1] = [before_main];
+
+fn main() {}
+```
+
+So, `#[used]` and `#[link_section]` can be combined to obtain "life before
+main".
+
+``` text
+$ rustc -C opt-level=3 before-main.rs
+
+$ ./before-main
+Hello, world!
+```
+
+Another example: ARM Cortex-M microcontrollers need their reset handler, a
+pointer to the function that will executed right after the microcontroller is
+turned on, to be placed near the start of their FLASH memory to boot properly.
+
+This condition can be met using `#[used]` and `#[link_section]` plus a linker
+script.
+
+``` rust
+#![feature(lang_items)]
+#![feature(used)]
+#![no_main]
+#![no_std]
+
+extern "C" fn reset_handler() -> ! {
+    loop {}
+}
+
+#[link_section = ".reset_handler"]
+#[used]
+static RESET_HANDLER: extern "C" fn() -> ! = reset_handler;
+
+#[lang = "panic_fmt"]
+fn panic_fmt() {}
+```
+
+``` text
+MEMORY
+{
+  FLASH : ORIGIN = 0x08000000, LENGTH = 128K
+  RAM : ORIGIN = 0x20000000, LENGTH = 20K
+}
+
+SECTIONS
+{
+  .text ORIGIN(FLASH) :
+  {
+    /* Vector table */
+    LONG(ORIGIN(RAM) + LENGTH(RAM)); /* initial SP value */
+    KEEP(*(.reset_handler));
+
+    /* Omitted: The rest of the vector table */
+
+    *(.text.*);
+  } > FLASH
+
+  /DISCARD/ :
+  {
+    /* Unused unwinding stuff */
+    *(.ARM.exidx.*)
+  }
+}
+```
+
+``` text
+$ xargo rustc --target thumbv7m-none-eabi --release -- \
+    -C link-arg=-Tlink.x -C link-arg=-nostartfiles
+
+$ arm-none-eabi-objdump -Cd target/thumbv7m-none-eabi/release/app
+./target/thumbv7m-none-eabi/release/app:     file format elf32-littlearm
+
+
+Disassembly of section .text:
+
+08000000 <app::RESET_HANDLER-0x4>:
+ 8000000:       20005000        .word   0x20005000
+
+08000004 <app::RESET_HANDLER>:
+ 8000004:       08000009                                ....
+
+08000008 <app::reset_handler>:
+ 8000008:       e7fe            b.n     8000008 <app::reset_handler>
+```