1//===-- sanitizer_local_address_space_view.h --------------------*- C++ -*-===//
2//
3//                     The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9//
10// `LocalAddressSpaceView` provides the local (i.e. target and current address
11// space are the same) implementation of the `AddressSpaveView` interface which
12// provides a simple interface to load memory from another process (i.e.
13// out-of-process)
14//
15// The `AddressSpaceView` interface requires that the type can be used as a
16// template parameter to objects that wish to be able to operate in an
17// out-of-process manner. In normal usage, objects are in-process and are thus
18// instantiated with the `LocalAddressSpaceView` type. This type is used to
19// load any pointers in instance methods. This implementation is effectively
20// a no-op. When an object is to be used in an out-of-process manner it is
21// instansiated with the `RemoteAddressSpaceView` type.
22//
23// By making `AddressSpaceView` a template parameter of an object, it can
24// change its implementation at compile time which has no run time overhead.
25// This also allows unifying in-process and out-of-process code which avoids
26// code duplication.
27//
28//===----------------------------------------------------------------------===//
29#ifndef SANITIZER_LOCAL_ADDRES_SPACE_VIEW_H
30#define SANITIZER_LOCAL_ADDRES_SPACE_VIEW_H
31
32namespace __sanitizer {
33struct LocalAddressSpaceView {
34  // Load memory `sizeof(T) * num_elements` bytes of memory from the target
35  // process (always local for this implementation) starting at address
36  // `target_address`. The local copy of this memory is returned as a pointer.
37  // The caller should not write to this memory. The behaviour when doing so is
38  // undefined. Callers should use `LoadWritable()` to get access to memory
39  // that is writable.
40  //
41  // The lifetime of loaded memory is implementation defined.
42  template <typename T>
43  static const T *Load(const T *target_address, uptr num_elements = 1) {
44    // The target address space is the local address space so
45    // nothing needs to be copied. Just return the pointer.
46    return target_address;
47  }
48
49  // Load memory `sizeof(T) * num_elements` bytes of memory from the target
50  // process (always local for this implementation) starting at address
51  // `target_address`. The local copy of this memory is returned as a pointer.
52  // The memory returned may be written to.
53  //
54  // Writes made to the returned memory will be visible in the memory returned
55  // by subsequent `Load()` or `LoadWritable()` calls provided the
56  // `target_address` parameter is the same. It is not guaranteed that the
57  // memory returned by previous calls to `Load()` will contain any performed
58  // writes.  If two or more overlapping regions of memory are loaded via
59  // separate calls to `LoadWritable()`, it is implementation defined whether
60  // writes made to the region returned by one call are visible in the regions
61  // returned by other calls.
62  //
63  // Given the above it is recommended to load the largest possible object
64  // that requires modification (e.g. a class) rather than individual fields
65  // from a class to avoid issues with overlapping writable regions.
66  //
67  // The lifetime of loaded memory is implementation defined.
68  template <typename T>
69  static T *LoadWritable(T *target_address, uptr num_elements = 1) {
70    // The target address space is the local address space so
71    // nothing needs to be copied. Just return the pointer.
72    return target_address;
73  }
74};
75}  // namespace __sanitizer
76
77#endif
78