diff --git a/doc/sphinx/reference/box/admin.rst b/doc/sphinx/reference/box/admin.rst
new file mode 100644
index 0000000000000000000000000000000000000000..b95bbd374309a53542c2f85a58700677c70d8fce
--- /dev/null
+++ b/doc/sphinx/reference/box/admin.rst
@@ -0,0 +1,63 @@
+.. include:: ../../directives.rst
+.. highlight:: lua
+
+-------------------------------------------------------------------------------
+                            Administrative requests
+-------------------------------------------------------------------------------
+
+To learn which functions are considered to be administrative, type ``help()``.
+A reference description also follows below:
+
+.. function:: box.snapshot()
+
+    Take a snapshot of all data and store it in _`snap_dir`/<latest-lsn>.snap.
+    To take a snapshot, Tarantool first enters the delayed garbage collection
+    mode for all data. In this mode, tuples which were allocated before the
+    snapshot has started are not freed until the snapshot has finished. To
+    preserve consistency of the primary key, used to iterate over tuples, a
+    copy-on-write technique is employed. If the master process changes part
+    of a primary key, the corresponding process page is split, and the snapshot
+    process obtains an old copy of the page. Since a snapshot is written
+    sequentially, one can expect a very high write performance (averaging to
+    80MB/second on modern disks), which means an average database instance gets
+    saved in a matter of minutes. Note, that as long as there are any changes to
+    the parent index memory through concurrent updates, there are going to be
+    page splits, and therefore one needs to have some extra free memory to run
+    this command. 10% of _`slab_alloc_arena` is, on average, sufficient. This
+    statement waits until a snapshot is taken and returns operation result.
+
+    .. code-block:: lua
+
+        tarantool> box.info.version
+        ---
+        - 1.6.3-439-g7e1011b
+        ...
+        tarantool> box.snapshot()
+        ---
+        - ok
+        ...
+        tarantool> box.snapshot()
+        ---
+        error: can't save snapshot, errno 17 (File exists)
+        ...
+
+
+    Taking a snapshot does not cause the server to start a new write-ahead log.
+    Once a snapshot is taken, old WALs can be deleted as long as all replicas
+    are up to date. But the WAL which was current at the time **box.snapshot()**
+    started must be kept for recovery, since it still contains log records
+    written after the start of **box.snapshot()**.
+
+    An alternative way to save a snapshot is to send the server SIGUSR1 UNIX
+    signal. While this approach could be handy, it is not recommended for use
+    in automation: a signal provides no way to find out whether the snapshot
+    was taken successfully or not.
+
+.. function:: coredump()
+
+    Fork and dump a core. Since Tarantool stores all tuples in memory, it can
+    take some time. Mainly useful for debugging.
+
+.. function:: require('fiber').info()
+
+    Show all running fibers, with their stack. Mainly useful for debugging.
diff --git a/doc/sphinx/reference/box/atomic.rst b/doc/sphinx/reference/box/atomic.rst
new file mode 100644
index 0000000000000000000000000000000000000000..fad312d47518435be20db1a70d56333ef7463625
--- /dev/null
+++ b/doc/sphinx/reference/box/atomic.rst
@@ -0,0 +1,90 @@
+.. include:: ../../directives.rst
+.. highlight:: lua
+
+-------------------------------------------------------------------------------
+                            Atomic execution
+-------------------------------------------------------------------------------
+
+In several places it's been noted that Lua processes occur in fibers on a
+single thread. That is why there can be a guarantee of execution atomicity.
+That requires emphasis.
+
+===========================================================
+            Cooperative multitasking environment
+===========================================================
+
+Tarantool core is built around a cooperative multi-tasking paradigm: unless a
+running fiber deliberately yields control to some other fiber, it is not
+preempted. “Yield points” are built into all calls from Tarantool core to the
+operating system. Any system call which can block is performed in an
+asynchronous manner and the fiber waiting on the system call is preempted with
+a fiber ready to run. This model makes all programmatic locks unnecessary:
+cooperative multitasking ensures that there is no concurrency around a resource,
+no race conditions and no memory consistency issues.
+
+When requests are small, e.g. simple UPDATE, INSERT, DELETE, SELECT, fiber
+scheduling is fair: it takes only a little time to process the request, schedule
+a disk write, and yield to a fiber serving the next client.
+
+A function, however, can perform complex computations, or be written in such a
+way that control is not given away for a long time. This can lead to unfair
+scheduling, when a single client throttles the rest of the system, or to
+apparent stalls in request processing. Avoiding this situation is the
+responsibility of the function's author. Most of the box calls, such as
+``box.space...insert``, ``box.space...update``, ``box.space...delete`` are yield
+points; ``box.space...select``, however, is not.
+
+It should also be noted that, in the absence of transactions, any yield in a
+function is a potential change in the database state. Effectively, it's only
+possible to have CAS (compare-and-swap) -like atomic stored procedures: i.e.
+functions which select and then modify a record. Multiple data change requests
+always run through a built-in yield point.
+
+At this point an objection could arise: "It's good that a single data-change
+request will commit and yield, but surely there are times when multiple
+data-change requests must happen without yielding." The standard example is the
+money-transfer, where $1 is withdrawn from account #1 and deposited into
+account #2. If something interrupted after the withdrawal, then the institution
+would be out of balance. For such cases, the ``begin ... commit|rollback`` block
+was designed.
+
+.. function:: box.begin()
+
+    From this point, implicit yields are suspended. In effect the fiber which
+    executes ``box.begin()`` is starting an "active multi-request transaction",
+    blocking all other fibers until the transaction ends. All operations within
+    this transaction should use the same storage engine.
+
+.. function:: box.commit()
+
+    End the currently active transaction, and make all its data-change
+    operations permanent.
+
+.. function:: box.rollback()
+
+    End the currently active transaction, but cancel all its data-change
+    operations. An explicit call to functions outside ``box.space`` that always
+    yield, such as ``fiber.yield`` or ``fiber.sleep``, will have the same effect.
+
+The *requests in a transaction must be sent to the server as a single block*.
+It is not enough to enclose them between ``begin`` and ``commit`` or ``rollback``.
+To ensure they are sent as a single block: put them in a function, or put them all
+on one line, or use a delimiter so that multi-line requests are handled together.
+
+===========================================================
+                         Example
+===========================================================
+
+Assuming that in tuple set 'tester' there are tuples in which the third
+field represents a positive dollar amount ... Start a transaction, withdraw from
+tuple#1, deposit in tuple#2, and end the transaction, making its effects permanent.
+
+.. code-block:: lua
+
+    console = require('console'); console.delimiter('!')
+    box.begin()
+    amount_of_money = 1.00
+    box.space.tester:update({999}, {{'-', 3, amount_of_money}})
+    box.space.tester:update({1000}, {{'+', 3, amount_of_money}})
+    box.commit()
+    console.delimiter('')!
diff --git a/doc/sphinx/reference/box/authentication.rst b/doc/sphinx/reference/box/authentication.rst
new file mode 100644
index 0000000000000000000000000000000000000000..bd887dac039a3821fe25b07b7b1564e2076d136f
--- /dev/null
+++ b/doc/sphinx/reference/box/authentication.rst
@@ -0,0 +1,345 @@
+.. include:: ../../directives.rst
+.. highlight:: lua
+
+-------------------------------------------------------------------------------
+                            Authentication and authorization
+-------------------------------------------------------------------------------
+
+Understanding the details of security is primarily an issue for administrators,
+but ordinary users should at least skim this section so that they will have an
+idea of how Tarantool makes it possible for administrators to prevent
+unauthorized access to the database and to certain functions.
+
+Briefly: there is a method to guarantee with password checks that users really
+are who they say they are ("authentication"). There is a _user space where user
+names and password-hashes are stored. There are functions for saying that
+certain users are allowed to do certain things ("privileges"). There is a _priv
+space where privileges are stored. Whenever a user tries to do an operation,
+there is a check whether the user has the privilege to do the operation
+("access control").
+
+===========================================================
+                        Passwords
+===========================================================
+
+Each user may have a password. The password is any alphanumeric string.
+Administrators should advise users to choose long unobvious passwords, but it
+is ultimately up to the users to choose or change their own passwords.
+
+Tarantool passwords are stored in the ``_user`` space with a `Cryptographic hash function`_
+so that, if the password is 'x', the stored hashed-password is a long string
+like '``lL3OvhkIPOKh+Vn9Avlkx69M/Ck=``'. When a client connects to a Tarantool
+server, the server sends a random `Salt Value`_ which the client must mix with the
+hashed-password before sending to the server. Thus the original value 'x' is
+never stored anywhere except in the user's head, and the hashed value is never
+passed down a network wire except when mixed with a random salt. This system
+prevents malicious onlookers from finding passwords by snooping in the log
+files or snooping on the wire. It is the same system that `MySQL introduced
+several years ago`_ which has proved adequate for medium-security installations.
+Nevertheless administrators should warn users that no system is foolproof against
+determined long-term attacks, so passwords should be guarded and changed occasionally.
+
+.. NOTE:
+
+    To get the hash-password of a string '``X``', say ``box.schema.user.password('X')``.
+    To see more about the details of the algorithm for the purpose of writing a new
+    client application, read the `scramble.h`_ header file.
+
+===========================================================
+                Users and the _user space
+===========================================================
+
+The fields in the ``_user`` space are: the numeric id of the tuple, the numeric
+id of the tuple's creator, the user name, the type, and the optional password.
+
+There are three special tuples in the _user space: 'guest', 'admin', and 'public'.
+
+.. container:: table
+
+    +--------+----+------+--------------------------------------------------------+
+    | Name   | ID | Type | Description                                            |
+    +========+====+======+========================================================+
+    | guest  | 0  | user | Default when connecting remotely. Usually an untrusted |
+    |        |    |      | user with few privileges.                              |
+    +--------+----+------+--------------------------------------------------------+
+    | admin  | 1  | user | Default when using ``tarantool`` as a console. Usually |
+    |        |    |      | an administrative user with all privileges.            |
+    +--------+----+------+--------------------------------------------------------+
+    | public | 2  | role | Not a user in the usual sense. Described later in      |
+    |        |    |      | section `Roles`_.                                      |
+    +--------+----+------+--------------------------------------------------------+
+
+To select a row from the ``_user`` space, use ``box.space._user:select``. For
+example, here is what happens with a select for user id = 0, which is the
+'guest' user, which by default has no password:
+
+.. code-block:: lua
+
+    tarantool> box.space._user:select{0}
+    ---
+    - - [0, 1, 'guest', 'user']
+    ...
+
+To change tuples in the ``_user`` space, do not use ordinary ``box.space``
+functions for insert or update or delete - the _user space is special so
+there are special functions which have appropriate error checking.
+
+To create a new user, say ``box.schema.user.create(user-name)`` or
+``box.schema.user.create(user-name, {password=password})``. The form
+``box.schema.user.create(user-name, {password=password})`` is better because
+in a `URI`_ (Uniform Resource Identifier) it is usually illegal to include a
+user-name without a password.
+
+To change the current user's password, say ``box.schema.user.passwd(password)``.
+
+To change a different user's password, say ``box.schema.user.passwd(user-name, password)``.
+(Only the admin user can perform this function.)
+
+To drop a user, say ``box.schema.user.drop(user-name)``.
+
+To check whether a user exists, say ``box.schema.user.exists(user-name)``,
+which returns true or false.
+
+For example, here is a session which creates a new user with a strong password,
+selects a tuple in the ``_user`` space, and then drops the user.
+
+.. code-block:: lua
+
+    tarantool> box.schema.user.create('JeanMartin', {password = 'Iwtso_6_os$$'})
+    ---
+    ...
+
+    tarantool> box.space._user.index.name:select{'JeanMartin'}
+    ---
+    - - [17, 1, 'JeanMartin', 'user', {'chap-sha1': 't3xjUpQdrt857O+YRvGbMY5py8Q='}]
+    ...
+
+    tarantool> box.schema.user.drop('JeanMartin')
+    ---
+    ...
+
+.. NOTE::
+
+    The maximum number of users is 32.
+
+===========================================================
+               Priveleges and _priv space
+===========================================================
+
+The fields in the ``_priv`` space are: the numeric id of the user who gave the
+privilege ("grantor_id"), the numeric id of the user who received the
+privilege ("grantee_id"), the id of the object, the type of object - "space"
+or "function" or "universe", the type of operation - "read" or "write" or
+"execute" or a combination such as "read,write,execute".
+
+The function for granting a privilege is:
+``box.schema.user.grant(user-name-of-grantee, operation-type, object-type, object-name)`` or
+``box.schema.user.grant(user-name-of-grantee, operation-type, 'universe')``.
+
+The function for revoking a privilege is:
+``box.schema.user.revoke(user-name-of-grantee, operation-type, object-type, object-name)`` or
+``box.schema.user.revoke(user-name-of-grantee, operation-type, 'universe')``.
+
+For example, here is a session where the admin user gave the guest user the
+privilege to read from a space named space55, and then took the privilege away:
+
+.. code-block:: lua
+
+    tarantool> box.schema.user.grant('guest', 'read', 'space', 'space55')
+    ---
+    ...
+    tarantool> box.schema.user.revoke('guest', 'read', 'space', 'space55')
+    ---
+    ...
+
+.. NOTE::
+
+    Generally privileges are granted or revoked by the owner of the object (the
+    user who created it), or by the 'admin' user. Before dropping any objects
+    or users, steps should be taken to ensure that all their associated
+    privileges have been revoked. Only the 'admin' user can grant privileges
+    for the 'universe'.
+
+
+===========================================================
+                Functions and _func space
+===========================================================
+
+The fields in the ``_func`` space are: the numeric function id, a number,
+and the function name.
+
+The ``_func`` space does not include the function's body. One continues to
+create Lua functions in the usual way, by saying
+"``function function_name () ... end``", without adding anything in the
+``_func`` space. The _func space only exists for storing function tuples so
+that their names can be used within grant/revoke functions.
+
+The function for creating a ``_func`` tuple is:
+``box.schema.func.create(function-name)``.
+
+The function for dropping a ``_func`` tuple is:
+``box.schema.func.drop(function-name)``.
+
+The function for checking whether a ``_func`` tuple exists is:
+``box.schema.func.exists(function-name)``.
+
+In the following example, a function named 'f7' is created, then it is put in
+the ``_func`` space, then it is used in a ``box.schema.user.grant`` function,
+then it is dropped:
+
+.. code-block:: lua
+
+    tarantool> function f7() box.session.uid() end
+    ---
+    ...
+    tarantool> box.schema.func.create('f7')
+    ---
+    ...
+    tarantool> box.schema.user.grant('guest', 'execute', 'function', 'f7')
+    ---
+    ...
+    tarantool> box.schema.user.revoke('guest', 'execute', 'function', 'f7')
+    ---
+    ...
+    tarantool> box.schema.func.drop('f7')
+    ---
+    ...
+
+===========================================================
+             ``box.session`` and security
+===========================================================
+
+After a connection has taken place, the user has access to a "session" object
+which has several functions. The ones which are of interest for security
+purposes are:
+
+.. code-block:: lua
+
+    box.session.uid()         -- returns the id of the current user
+    box.session.user()        -- returns the name of the current user
+    box.session.su(user-name) -- allows changing current user to 'user-name'
+
+If a user types requests directly on the Tarantool server in its interactive
+mode, or if a user connects via telnet to the administrative port (using `admin`_
+instead of listen), then the user by default is 'admin' and has many privileges.
+If a user connects from an application program via one of the `connectors`_, then
+the user by default is 'guest' and has few privileges. Typically an admin user
+will set up and configure objects, then grant privileges to appropriate non-admin
+users. Typically a guest user will use ``box.session.su()`` to change into a non-generic
+user to whom admin has granted more than the default privileges. For example,
+admin might say:
+
+.. code-block:: lua
+
+    box.space._user:insert{123456,0,'manager'}
+    box.schema.user.grant('manager', 'read', 'space', '_space')
+    box.schema.user.grant('manager', 'read', 'space', 'payroll')
+
+and later a guest user, who wishes to see the payroll, might say:
+
+.. code-block:: lua
+
+    box.session.su('manager')
+    box.space.payroll:select{'Jones'}
+
+===========================================================
+                         Roles
+===========================================================
+
+A role is a container for privileges which can be granted to regular users.
+Instead of granting and revoking individual privileges, one can put all the
+privileges in a role and then grant or revoke the role. Role information is
+in the ``_user`` space but the third field - the type field - is 'role' rather
+than 'user'.
+
+If a role R1 is granted a privilege X, and user U1 is granted a privilege
+"role R1", then user U1 in effect has privilege X. Then if a role R2 is
+granted a privilege Y, and role R1 is granted a privilege "role R2",
+then user U1 in effect has both privilege X and privilege Y. In other words,
+a user gets all the privileges that are granted to a user's roles, directly
+or indirectly.
+
+.. module:: box.schema.role
+
+.. function:: create(role-name)
+
+    Create a new role.
+
+.. function:: grant(role-name, privilege)
+
+    Put a privilege in a role.
+
+.. function:: revoke(role-name, privilege)
+
+    Take a privilege out of a role.
+
+.. function:: drop(role-name)
+
+    Drop a role.
+
+.. function:: info()
+
+    Get information about a role.
+
+.. function:: grant(role-name, 'execute', 'role', role-name)
+
+    Grant a role to a role.
+
+.. function:: revoke(role-name, 'execute', 'role', role-name)
+
+    Revoke a role from a role.
+
+.. function:: exists(role-name)
+
+    Check whether a role exists.
+    :return: true if role-name identifies a role, otherwise false.
+    :rtype:  boolean
+
+.. module:: box.schema.user
+
+.. function:: grant(user-name, 'execute', 'role', role-name)
+
+    Grant a role to a user.
+
+.. function:: revoke(user-name, 'execute', 'role', role-name)
+
+    Revoke a role from a user.
+
+There is one predefined role, named 'public', which is automatically assigned
+to new users when they are created with ``box.schema.user.create(user-name)``.
+Therefore a convenient way to grant 'read' on space '``t``' to every user that
+will ever exist is:
+
+.. code-block:: lua
+
+    box.schema.role.grant('public','read','space','t').
+
+===========================================================
+                         Example
+===========================================================
+
+In this example, a new user named U1 will insert a new tuple into a new space
+named T, and will succeed even though user U1 has no direct privilege to do
+such an insert -- that privilege is inherited from role R1, which in turn
+inherits from role R2.
+
+.. code-block:: lua
+
+    -- This example will work for a user with many privileges, such as 'admin'
+    box.schema.space.create('T')
+    box.space.T:create_index('primary',{})
+    -- Create a user U1 so that later it's possible to say box.session.su('U1')
+    box.schema.user.create('U1')
+    -- Create two roles, R1 and R2
+    box.schema.role.create('R1')
+    box.schema.role.create('R2')
+    -- Grant role R2 to role R1 and role R1 to U1 (order doesn't matter)
+    box.schema.role.grant('R1','execute','role','R2')
+    box.schema.role.grant('U1','execute','role','R1')
+    -- Grant read and execute privileges to R2 (but not to R1 and not to U1)
+    box.schema.role.grant('R2','read,write','space','T')
+    box.schema.role.grant('R2','execute','universe')
+    -- Use box.session.su to say "now become user U1"
+    box.session.su('U1')
+    -- The following insert succeeds because U1 in effect has write privilege on T
+    box.space.T:insert{1}
diff --git a/doc/sphinx/reference/box/box_error.rst b/doc/sphinx/reference/box/box_error.rst
new file mode 100644
index 0000000000000000000000000000000000000000..f900b5c7ecf54421d651f446ad488267dd2f8852
--- /dev/null
+++ b/doc/sphinx/reference/box/box_error.rst
@@ -0,0 +1,61 @@
+.. include:: ../../directives.rst
+.. highlight:: lua
+
+-------------------------------------------------------------------------------
+                            Package `box.error`
+-------------------------------------------------------------------------------
+
+The ``box.error`` function is for raising an error. The difference between this
+function and Lua's built-in ``error()`` function is that when the error reaches
+the client, its error code is preserved. In contrast, a Lua error would always
+be presented to the client as ``ER_PROC_LUA``.
+
+.. module:: box.error
+
+.. function:: box.error{reason=string [, code=number]}
+
+    When called with a Lua-table argument, the code and reason have any
+    user-desired values. The result will be those values.
+
+    :param integer  code:
+    :param string reason:
+
+.. function:: box.error()
+
+    When called without arguments, ``box.error()`` re-throws whatever the last
+    error was.
+
+.. function:: box.error(code, errtext [, errtext ...])
+
+    Emulate a request error, with text based on one of the pre-defined Tarantool
+    errors defined in the file _`errcode.h` in the source tree. Lua constants
+    which correspond to those Tarantool errors are defined as members of
+    ``box.error``, for example ``box.error.NO_SUCH_USER == 45``.
+
+    :param number       code: number of a pre-defined error
+    :param string errtext(s): part of the message which will accompany the error
+
+    For example:
+
+    the ``NO_SUCH_USER`` message is "``User '%s' is not found``" -- it includes
+    one "``%s``" component which will be replaced with errtext. Thus a call to
+    ``box.error(box.error.NO_SUCH_USER, 'joe')`` or ``box.error(45, 'joe')``
+    will result in an error with the accompanying message
+    "``User 'joe' is not found``".
+
+    :except: whatever is specified in errcode-number.
+
+    .. code-block:: lua
+
+        tarantool> box.error({code=555, reason='Arbitrary message'})
+        ---
+        - error: Arbitrary message
+        ...
+        tarantool> box.error()
+        ---
+        - error: Arbitrary message
+        ...
+        tarantool> box.error(box.error.FUNCTION_ACCESS_DENIED, 'A', 'B', 'C')
+        ---
+        - error: A access denied for user 'B' to function 'C'
+        ...
diff --git a/doc/sphinx/reference/box/box_introspection.rst b/doc/sphinx/reference/box/box_introspection.rst
new file mode 100644
index 0000000000000000000000000000000000000000..b2aa690fa14c4f0991d743b724b31e6019367dfc
--- /dev/null
+++ b/doc/sphinx/reference/box/box_introspection.rst
@@ -0,0 +1,222 @@
+.. include:: ../../directives.rst
+.. highlight:: lua
+
+-------------------------------------------------------------------------------
+                            Server Introspection
+-------------------------------------------------------------------------------
+
+=====================================================================
+                         Package `box.cfg`
+=====================================================================
+
+.. module:: box.cfg
+
+The ``box.cfg`` package is for administrators to specify all the server
+configuration parameters; the full description of the parameters is in
+section Configuration_. Use ``box.cfg`` without braces to get read-only
+access to those parameters.
+
+.. data:: box.cfg
+
+    .. code-block:: lua
+
+        tarantool> box.cfg
+        ---
+        - too_long_threshold: 0.5
+          slab_alloc_factor: 2
+          slab_alloc_minimal: 64
+          background: false
+          slab_alloc_arena: 1
+          log_level: 5
+          ...
+        ...
+
+.. _Configuration: http://tarantool.org/doc/user_guide.html#configuration-file
+
+=====================================================================
+                         Package `box.info`
+=====================================================================
+
+.. module:: box.info
+
+The ``box.info`` package provides access to information about server variables
+-- ``pid``, ``uptime``, ``version`` and others.
+
+**recovery_lag** holds the difference (in seconds) between the current time on
+the machine (wall clock time) and the time stamp of the last applied record.
+In replication setup, this difference can indicate the delay taking place
+before a change is applied to a replica.
+
+**recovery_last_update** is the wall clock time of the last change recorded in
+the write-ahead log. To convert it to human-readable time,
+you can use **date -d@** 1306964594.980.
+
+**status** is either "primary" or "replica/<hostname>".
+
+.. function:: box.info()
+
+    Since ``box.info`` contents are dynamic, it's not possible to iterate over
+    keys with the Lua ``pairs()`` function. For this purpose, ``box.info()``
+    builds and returns a Lua table with all keys and values provided in the
+    package.
+
+    :return: keys and values in the package.
+    :rtype:  table
+
+    .. code-block:: yaml
+
+        tarantool> box.info()
+        ---
+        - server:
+            lsn: 158
+            ro: false
+            uuid: 75967704-0115-47c2-9d03-bd2bdcc60d64
+            id: 1
+          pid: 32561
+          version: 1.6.4-411-gcff798b
+          snapshot_pid: 0
+          status: running
+          vclock: {1: 158}
+          replication:
+            status: off
+          uptime: 2778
+        ...
+
+.. data:: status
+          pid
+          version
+          ...
+
+    .. code-block:: lua
+
+        tarantool> box.info.pid
+        ---
+        - 1747
+        ...
+        tarantool> box.info.logger_pid
+        ---
+        - 1748
+        ...
+        tarantool> box.info.version
+        ---
+        - 1.6.4-411-gcff798b
+        ...
+        tarantool> box.info.uptime
+        ---
+        - 3672
+        ...
+        tarantool> box.info.status
+        ---
+        - running
+        ...
+        tarantool> box.info.recovery_lag
+        ---
+        - 0.000
+        ...
+        tarantool> box.info.recovery_last_update
+        ---
+        - 1306964594.980
+        ...
+        tarantool> box.info.snapshot_pid
+        ---
+        - 0
+        ...
+
+=====================================================================
+                         Package `box.slab`
+=====================================================================
+
+.. module:: box.slab
+
+The ``box.slab`` package provides access to slab allocator statistics. The
+slab allocator is the main allocator used to store tuples. This can be used
+to monitor the total memory use and memory fragmentation.
+
+The display of slabs is broken down by the slab size -- 64-byte, 136-byte,
+and so on. The example omits the slabs which are empty. The example display
+is saying that: there are 16 items stored in the 64-byte slab (and 16*64=102
+so bytes_used = 1024); there is 1 item stored in the 136-byte slab
+(and 136*1=136 so bytes_used = 136); the arena_used value is the total of all
+the bytes_used values (1024+136 = 1160); the arena_size value is the arena_used
+value plus the total of all the bytes_free values (1160+4193200+4194088 = 8388448).
+The arena_size and arena_used values are the amount of the % of slab_alloc_arena
+that is already distributed to the slab allocator.
+
+.. data:: slab
+
+    .. code-block:: lua
+
+        tarantool> box.slab.info().arena_used
+        ---
+        - 4194304
+        ...
+        tarantool> box.slab.info().arena_size
+        ---
+        - 104857600
+        ...
+        tarantool> box.slab.info().slabs
+        ---
+        - - {mem_free: 9320, mem_used: 6976, 'item_count': 109,
+            'item_size': 64, 'slab_count': 1, 'slab_size': 16384}
+          - {mem_free: 16224, mem_used: 72, 'item_count': 1,
+            'item_size': 72, 'slab_count': 1,'slab_size': 16384}
+        etc.
+        ...
+        tarantool> box.slab.info().slabs[1]
+        ---
+        - {mem_free: 9320, mem_used: 6976, 'item_count': 109,
+          'item_size': 64, 'slab_count': 1, 'slab_size': 16384}
+        ...
+
+=====================================================================
+                         Package `box.stat`
+=====================================================================
+
+.. module:: box.stat
+
+The ``box.stat`` package provides access to request statistics. Show the
+average number of requests per second, and the total number of requests
+since startup, broken down by request type.
+
+.. data:: box.stat
+
+    .. code-block:: lua
+
+        tarantool> box.stat, type(box.stat) -- a virtual table
+        ---
+        - []
+        - table
+        ...
+        tarantool> box.stat() -- the full contents of the table
+        ---
+        - DELETE:
+            total: 48902544
+            rps: 147
+          EVAL:
+            total: 0
+            rps: 0
+          SELECT:
+            total: 388322317
+            rps: 1246
+          REPLACE:
+            total: 4
+            rps: 0
+          INSERT:
+            total: 48207694
+            rps: 139
+          AUTH:
+            total: 0
+            rps: 0
+          CALL:
+            total: 8
+            rps: 0
+          UPDATE:
+            total: 743350520
+            rps: 1874
+        ...
+        tarantool> box.stat().DELETE -- a selected item of the table
+        ---
+        - total: 48902544
+          rps: 0
+        ...
+
diff --git a/doc/sphinx/reference/box_session.rst b/doc/sphinx/reference/box/box_session.rst
similarity index 98%
rename from doc/sphinx/reference/box_session.rst
rename to doc/sphinx/reference/box/box_session.rst
index e11522b0e480e19bbb295694da3e9f769559f6a0..49cd6c2d1649b27203d733891997da9ddc425ab9 100644
--- a/doc/sphinx/reference/box_session.rst
+++ b/doc/sphinx/reference/box/box_session.rst
@@ -1,4 +1,4 @@
-.. include:: ../directives.rst
+.. include:: ../../directives.rst
 .. highlight:: lua
 
 -------------------------------------------------------------------------------
diff --git a/doc/sphinx/reference/box/box_tuple.rst b/doc/sphinx/reference/box/box_tuple.rst
new file mode 100644
index 0000000000000000000000000000000000000000..b2912b5c504fd47ff682622743ca9a992119c469
--- /dev/null
+++ b/doc/sphinx/reference/box/box_tuple.rst
@@ -0,0 +1,307 @@
+.. include:: ../../directives.rst
+.. highlight:: lua
+
+-------------------------------------------------------------------------------
+                            Package `box.tuple`
+-------------------------------------------------------------------------------
+
+.. module:: box.tuple
+
+The ``box.tuple`` package provides read-only access for the ``box.tuple``
+userdata type. It allows, for a single tuple: selective retrieval of the field
+contents, retrieval of information about size, iteration over all the fields,
+and conversion to a Lua table.
+
+.. function:: new(value)
+
+    Construct a new tuple from either a scalar or a Lua table. Alternatively,
+    one can get new tuples from tarantool's SQL-like statements: SELECT,
+    INSERT, UPDATE, REPLACE, which can be regarded as statements that do
+    ``new()`` implicitly.
+
+    :param lua-value value: the value that will become the tuple contents.
+
+    :return: a new tuple
+    :rtype:  tuple
+
+    In the following example, ``x`` will be a new table object containing one
+    tuple and ``t`` will be a new tuple object. Saying ``t`` returns the
+    entire tuple ``t``.
+
+    .. code-block:: lua
+
+        tarantool> x = box.space.tester:insert{33,tonumber('1'),tonumber64('2')}:totable()
+        ---
+        ...
+        tarantool> t = box.tuple.new({'abc', 'def', 'ghi', 'abc'})
+        ---
+        ...
+        tarantool> t
+        ---
+        - ['abc', 'def', 'ghi', 'abc']
+        ...
+
+.. class:: tuple
+
+    .. method:: __len()
+
+        The ``#`` operator in Lua means "return count of components". So,
+        if ``t`` is a tuple instance, ``#t`` will return the number of fields.
+
+        :rtype: number
+
+        In the following example, a tuple named ``t`` is created and then the
+        number of fields in ``t`` is returned.
+
+        .. code-block:: lua
+
+            tarantool> t = box.tuple.new({'Fld#1','Fld#2','Fld#3','Fld#4'})
+            ---
+            ...
+            tarantool> #t
+            ---
+            - 4
+            ...
+
+    .. method:: bsize()
+
+        If ``t`` is a tuple instance, ``t:bsize()`` will return the number of
+        bytes in the tuple. It is useful to check this number when making
+        changes to data, because there is a fixed maximum: one megabyte. Every
+        field has one or more "length" bytes preceding the actual contents, so
+        ``bsize()`` returns a value which is slightly greater than the sum of
+        the lengths of the contents.
+
+        :return: number of bytes
+        :rtype: number
+
+        In the following example, a tuple named ``t`` is created which has
+        three fields, and for each field it takes one byte to store the length
+        and three bytes to store the contents, and a bit for overhead, so
+        ``bsize()`` returns ``3*(1+3)+1``.
+
+        .. code-block:: lua
+
+            tarantool> t = box.tuple.new({'aaa','bbb','ccc'})
+            ---
+            ...
+            tarantool> t:bsize()
+            ---
+            - 13
+            ...
+
+    .. method:: __index(key)
+
+        If ``t`` is a tuple instance, ``t[field-number]`` will return the field
+        numbered field-number in the tuple. The first field is ``t[1]``.
+
+        :return: field value.
+        :rtype:  lua-value
+
+        In the following example, a tuple named ``t`` is created and then the
+        second field in ``t`` is returned.
+
+        .. code-block:: lua
+
+            tarantool> t = box.tuple.new({'Fld#1','Fld#2','Fld#3','Fld#4'})
+            ---
+            ...
+            tarantool> t[2]
+            ---
+            - Fld#2
+            ...
+
+    .. method:: find([field-number,] field-value)
+                findall([field-number,] field-value)
+
+        If ``t`` is a tuple instance, ``t:find(field-value)`` will return the
+        number of the first field in ``t`` that matches the field value),
+        and ``t:findall(field-value [, field-value ...])`` will return numbers
+        of all fields in ``t`` that match the field value. Optionally one can
+        put a numeric argument ``field-number`` before the search-value to
+        indicate “start searching at field number ``field-number``.”
+
+        :return: the number of the field in the tuple.
+        :rtype:  number
+
+        In the following example, a tuple named ``t`` is created and then: the
+        number of the first field in ``t`` which matches 'a' is returned, then
+        the numbers of all the fields in ``t`` which match 'a' are returned,
+        then the numbers of all the fields in t which match 'a' and are at or
+        fter the second field are returned.
+
+        .. code-block:: lua
+
+            tarantool> t = box.tuple.new({'a','b','c','a'})
+            ---
+            ...
+            tarantool> t:find('a')
+            ---
+            - 1
+            ...
+            tarantool> t:findall('a')
+            ---
+            - 1
+            - 4
+            ...
+            tarantool> t:findall(2, 'a')
+            ---
+            - 4
+            ...
+
+    .. method:: transform(start-field-number, fields-to-remove [, field-value ...])
+
+        If ``t`` is a tuple instance, ``t:transform(start-field-number,fields-to-remove)``
+        will return a tuple where, starting from field ``start-field-number``,
+        a number of fields (``fields-to-remove``) are removed. Optionally one
+        can add more arguments after ``fields-to-remove`` to indicate new
+        values that will replace what was removed.
+
+        :param integer start-field-number: base 1, may be negative
+        :param integer   fields-to-remove:
+        :param lua-value   field-value(s):
+        :return: tuple
+        :rtype:  tuple
+
+        In the following example, a tuple named ``t`` is created and then,
+        starting from the second field, two fields are removed but one new
+        one is added, then the result is returned.
+
+        .. code-block:: lua
+
+            tarantool> t = box.tuple.new({'Fld#1','Fld#2','Fld#3','Fld#4','Fld#5'})
+            ---
+            ...
+            tarantool> t:transform(2,2,'x')
+            ---
+            - ['Fld#1', 'x', 'Fld#4', 'Fld#5']
+            ...
+
+    .. method:: unpack()
+
+        If ``t`` is a tuple instance, ``t:unpack(n)`` will return all fields.
+
+        :return: field(s) from the tuple.
+        :rtype:  lua-value(s)
+
+        In the following example, a tuple named ``t`` is created and then all
+        its fields are selected, then the result is returned.
+
+        .. code-block:: lua
+
+            tarantool> t = box.tuple.new({'Fld#1','Fld#2','Fld#3','Fld#4','Fld#5'})
+            ---
+            ...
+            tarantool> t:unpack()
+            ---
+            - Fld#1
+            - Fld#2
+            - Fld#3
+            - Fld#4
+            - Fld#5
+            ...
+
+    .. method:: pairs()
+
+        In Lua, ``lua-table-value:pairs()`` is a method which returns:
+        ``function``, ``lua-table-value``, ``nil``. Tarantool has extended
+        this so that ``tuple-value:pairs()`` returns: ``function``,
+        ``tuple-value``, ``nil``. It is useful for Lua iterators, because Lua
+        iterators traverse a value's components until an end marker is reached.
+
+        :return: function, tuple-value, nil
+        :rtype:  function, lua-value, nil
+
+        In the following example, a tuple named ``t`` is created and then all
+        its fields are selected using a Lua for-end loop.
+
+        .. code-block:: lua
+
+            tarantool> t = box.tuple.new({'Fld#1','Fld#2','Fld#3','Fld#4','Fld#5'})
+            ---
+            ...
+            tarantool> tmp = ''; for k, v in t:pairs() do tmp = tmp .. v end
+            ---
+            ...
+            tarantool> tmp
+            ---
+            - Fld#1Fld#2Fld#3Fld#4Fld#5
+            ...
+
+    .. method:: update({{format, field_number, value}...})
+
+        Update a tuple.
+
+        This function updates a tuple which is not in a space. Compare the function
+        ``box.space.space-name:update{key, format, {field_number, value}...)``,
+        which updates a tuple in a space.
+
+        Parameters: briefly: format indicates the type of update operation such as '``=``'
+        for 'assign new value', ``field_number`` indicates the field number to change such
+        as 2 for field number 2, value indicates the string which operates on the field such
+        as 'B' for a new assignable value = 'B'.
+
+        For details: see the description for ``format``, ``field_number``, and ``value`` in
+        the section ``box.space.space-name:update{key, format, {field_number, value}...)``.
+
+        :return: new tuple
+        :rtype:  tuple
+
+        In the following example, a tuple named ``t`` is created and then its second field is
+        updated to equal 'B'.
+
+        .. code-block:: lua
+
+            tarantool> t = box.tuple.new({'Fld#1','Fld#2','Fld#3','Fld#4','Fld#5'})
+            ---
+            ...
+            tarantool> t:update({{'=',2,'B'}})
+            ---
+            - ['Fld#1', 'B', 'Fld#3', 'Fld#4', 'Fld#5']
+            ...
+
+===========================================================
+                        Example
+===========================================================
+
+This function will illustrate how to convert tuples to/from Lua tables and
+lists of scalars:
+
+.. code-block:: lua
+
+    tuple = box.tuple.new({scalar1, scalar2, ... scalar_n}) -- scalars to tuple
+    lua_table = {tuple:unpack()}                            -- tuple to Lua table
+    scalar1, scalar2, ... scalar_n = tuple:unpack()         -- tuple to scalars
+    tuple = box.tuple.new(lua_table)                        -- Lua table to tuple
+
+Then it will find the field that contains 'b', remove that field from the tuple,
+and display how many bytes remain in the tuple. The function uses Tarantool
+``box.tuple`` functions ``new()``, ``unpack()``, ``find()``, ``transform()``,
+``bsize()``.
+
+.. code-block:: lua
+
+    console = require('console'); console.delimiter('!')
+    function example()
+      local tuple1, tuple2, lua_table_1, scalar1, scalar2, scalar3, field_number
+      tuple1 = box.tuple.new({'a', 'b', 'c'})
+      luatable1 = {tuple1:unpack()}
+      scalar1, scalar2, scalar3 = tuple1:unpack()
+      tuple2 = box.tuple.new(luatable1)
+      field_number = tuple2:find('b')
+      tuple2 = tuple2:transform(field_number, 1)
+      return 'tuple2 = ' , tuple2 , ' # of bytes = ' , tuple2:bsize()
+    end!
+    console.delimiter('')!
+
+... And here is what happens when one invokes the function:
+
+.. code-block:: yaml
+
+    tarantool> example()
+    ---
+    - 'tuple2 = '
+    - ['a', 'c']
+    - ' # of bytes = '
+    - 5
+    ...
diff --git a/doc/sphinx/reference/box/index.rst b/doc/sphinx/reference/box/index.rst
index f2726d03d96c1bb9614381dba1d71356c9c46c74..ee5f827a0dd4bb5597f737900c45823c1958f51a 100644
--- a/doc/sphinx/reference/box/index.rst
+++ b/doc/sphinx/reference/box/index.rst
@@ -19,11 +19,15 @@ no arguments. The packages inside the box library are:
     box_tuple
     box_space
     box_index
+    box_session
+    box_error
+    box_tuple
+    box_introspection
     net_box
-    box_cfg
-    box_info
-    box_slab
-    box_stat
+    admin
+    atomic
+    authentication
+    limitations
 
 Every package contains one or more Lua functions. A few packages contain
 members as well as functions. The functions allow data definition (create
diff --git a/doc/sphinx/reference/box/limitations.rst b/doc/sphinx/reference/box/limitations.rst
new file mode 100644
index 0000000000000000000000000000000000000000..c1c279df7afc7ee92a5c3c351a469f174af09a5a
--- /dev/null
+++ b/doc/sphinx/reference/box/limitations.rst
@@ -0,0 +1,49 @@
+.. include:: ../../directives.rst
+.. highlight:: lua
+
+-------------------------------------------------------------------------------
+                            Limitations
+-------------------------------------------------------------------------------
+
+Number of fields in an index
+    For BITSET indexes, the maximum is 1. For TREE or HASH indexes, the maximum
+    is 255 (``box.schema.INDEX_PART_MAX``). For RTREE indexes, the number of
+    fields must be either 2 or 4.
+
+Number of indexes in a space
+    10 (``box.schema.INDEX_MAX``).
+
+Number of fields in a tuple
+    The theoretical maximum is 2147483647 (``box.schema.FIELD_MAX``). The
+    practical maximum is whatever is specified by the space's field_count
+    member, or the maximum tuple length.
+
+Number of spaces
+    The theoretical maximum is 2147483647 (``box.schema.SPACE_MAX``).
+
+Number of connections
+    The practical limit is the number of file descriptors that one can set
+    with the operating system.
+
+Space size
+    The total maximum size for all spaces is in effect set by
+    `slab_alloc_arena`_, which in turn is limited by the total available memory.
+
+Update operations count
+    The maximum number of operations that can be in a single update
+    is 4000 (``BOX_UPDATE_OP_CNT_MAX``).
+
+Number of users and roles
+    32 ().
+
+Length of an index name or space name or user name
+    32 (``box.schema.NAME_MAX``).
+
+Limitations which are only applicable for the sophia storage engine
+    The maximum number of fields in an index is always 1, that is, multi-part
+    indexes are not supported. The maximum number of indexes in a space is
+    always 1, that is, secondary indexes are not supported. Indexes must be
+    unique, that is, the options type=HASH or type=RTREE or type=BITSET are
+    not supported. Indexes must be unique, that is, the option unique=false
+    is not supported. The ``alter()``, ``len()``, and ``count()`` functions
+    are not supported.
diff --git a/doc/sphinx/reference/box/net_box.rst b/doc/sphinx/reference/box/net_box.rst
new file mode 100644
index 0000000000000000000000000000000000000000..98ef99f5ce4a5c6c8eca6b1188aa18b025a7ed2d
--- /dev/null
+++ b/doc/sphinx/reference/box/net_box.rst
@@ -0,0 +1,241 @@
+.. include:: ../../directives.rst
+.. highlight:: lua
+
+-------------------------------------------------------------------------------
+                            Package `net.box`
+-------------------------------------------------------------------------------
+
+The ``net.box`` package contains connectors to remote database systems. One
+variant, ``box.net.sql``, is for connecting to MySQL or MariaDB or PostgreSQL —
+that variant is the subject of the `SQL DBMS plugins`_ appendix. In this section
+the subject is the built-in variant, ``box.net``. This is for connecting to
+tarantool servers via a network.
+
+Call ``require('net.box')`` to get a ``net.box`` object, which will be called
+``net_box`` for examples in this section. Call ``net_box.new()`` to connect and
+get a connection object, which will be called conn for examples in this section.
+Call the other ``net.box()`` routines, passing ``conn:``, to execute requests on
+the remote box. Call `conn:close`_ to disconnect.
+
+.. _conn:close: :func:`connection_object:close`
+
+All `net.box`` methods are fiber-safe, that is, it is safe to share and use the
+same connection object across multiple concurrent fibers. In fact, it's perhaps
+the best programming practice with Tarantool. When multiple fibers use the same
+connection, all requests are pipelined through the same network socket, but each
+fiber gets back a correct response. Reducing the number of active sockets lowers
+the overhead of system calls and increases the overall server performance. There
+are, however, cases when a single connection is not enough — for example when it's
+necessary to prioritize requests or to use different authentication ids.
+
+.. module:: net_box
+
+.. function:: new(host, port [, {params}])
+
+    Create a new connection. The connection is established on demand, at the
+    time of the first request. It is re-established automatically after a
+    disconnect. The returned conn object supports methods for making remote
+    requests, such as select, update or delete.
+
+    For the local tarantool server there is a pre-created always-established
+    connection object named net_box.self. Its purpose is to make polymorphic
+    use of the ``net_box`` API easier. Therefore ``conn = net_box:new('localhost', 3301)``
+    can be replaced by ``conn = net_box.self``. However, there is an important
+    difference between the embedded connection and a remote one. With the
+    embedded connection, requests which do not modify data do not yield.
+    When using a remote connection, any request can yield, and local database
+    state may have changed by the time it returns.
+
+    :param string host:
+    :param number port:
+    :param boolean wait_connect:
+    :param string user:
+    :param string password:
+    :return: conn object
+    :rtype:  userdata
+
+    .. code-block:: lua
+
+        conn = net_box:new('localhost', 3301)
+        conn = net_box:new('127.0.0.1', box.cfg.listen, {
+            wait_connect = false,
+            user = 'guest',
+            password = ''
+        })
+
+.. class:: connection
+
+    .. method:: ping()
+
+        Execute a PING command.
+
+        :return: true on success, false on error
+        :rtype:  boolean
+
+        .. code-block:: lua
+
+            net_box.self:ping()
+
+    .. method:: wait_connected([timeout])
+
+        Wait for connection to be active or closed.
+
+        :param number timeout:
+        :return: true when connected, false on failure.
+        :rtype:  boolean
+
+        .. code-block:: lua
+
+            net_box.self:wait_connected().
+
+    .. method:: close()
+
+        Close a connection.
+
+        Connection objects are garbage collected just like any other objects in Lua, so
+        an explicit destruction is not mandatory. However, since close() is a system
+        call, it is good programming practice to close a connection explicitly when it
+        is no longer needed, to avoid lengthy stalls of the garbage collector.
+
+        .. code-block:: lua
+
+            conn:close()
+
+    .. method:: connection.space.<space-name>:select{field-value, ...}
+
+        ``conn.space.space-name:select{...}`` is the remote-call equivalent
+        of the local call ``box.space.space-name:select{...}``. Please note
+        this difference: a local ``box.space.space-name:select{...}`` does
+        not yield, but a remote ``conn.space.space-name:select{...}`` call
+        does yield, so local data may change while a remote
+        ``conn.space.space-name:select{...}`` is running.
+
+    .. method:: connection.space.<space-name>:insert{field-value, ...}
+
+        ``conn.space.space-name:insert(...)`` is the remote-call equivalent
+        of the local call ``box.space.space-name:insert(...)``.
+
+    .. method:: connection.space.<space-name>:replace{field-value, ...}
+
+        ``conn.space.space-name:replace(...)`` is the remote-call equivalent
+        of the local call ``box.space.space-name:replace(...)``.
+
+    .. method:: connection.space.<space-name>:update{field-value, ...}
+
+        ``conn.space.space-name:update(...)`` is the remote-call equivalent
+        of the local call ``box.space.space-name:update(...)``.
+
+    .. method:: connection.space.<space-name>:delete{field-value, ...}
+
+        ``conn.space.space-name:delete(...)`` is the remote-call equivalent
+        of the local call ``box.space.space-name:delete(...)``.
+
+    .. method:: call(function-name [, arguments])
+
+        ``conn:call('func', '1', '2', '3')`` is the remote-call equivalent of
+        ``func('1', '2', '3')``. That is, ``conn:call`` is a remote
+        stored-procedure call.
+
+        .. code-block:: lua
+
+            conn:call('function5').
+
+    .. method:: timeout(timeout)
+
+        ``timeout(...)`` is a wrapper which sets a timeout for the request that
+        follows it.
+
+        .. code-block:: lua
+
+            conn:timeout(0.5).space.tester:update({1}, {{'=', 2, 15}}).
+
+        All remote calls support execution timeouts. Using a wrapper object makes
+        the remote connection API compatible with the local one, removing the need
+        for a separate timeout argument, which the local version would ignore. Once
+        a request is sent, it cannot be revoked from the remote server even if a
+        timeout expires: the timeout expiration only aborts the wait for the remote
+        server response, not the request itself.
+
+.. _SQL DBMS plugins: http://tarantool.org/doc/user_guide.html#plugins
+
+===========================================================
+                        Example
+===========================================================
+
+This example will work with the sandbox configuration described in the preface.
+That is, there is a space named tester with a numeric primary key. Assume that
+the database is nearly empty. Assume that the tarantool server is running on
+``localhost 127.0.0.1:3301``.
+
+.. code-block:: lua
+
+    tarantool> box.schema.user.grant('guest', 'read,write,execute', 'universe')
+    ---
+    ...
+    tarantool> console = require('console'); console.delimiter('!')
+    ---
+    ...
+    tarantool> net_box = require('net.box')!
+    ---
+    ...
+    tarantool> function example()
+             > if net_box.self:ping() then
+             >   table.insert(ta, 'self:ping() succeeded')
+             >   table.insert(ta, '  (no surprise -- self connection is pre-established)')
+             > end
+             > if box.cfg.listen == '3301' then
+             >   table.insert(ta,'The local server listen address = 3301')
+             > else
+             >   table.insert(ta, 'The local server listen address is not 3301')
+             >   table.insert(ta, '(  (maybe box.cfg{...listen="3301"...} was not stated)')
+             >   table.insert(ta, '(  (so connect will fail)')
+             > end
+             > conn = net_box:new('127.0.0.1', 3301)
+             > conn.space.tester:delete{800}
+             > table.insert(ta, 'conn delete done on tester.')
+             > conn.space.tester:insert{800, 'data'}
+             > table.insert(ta, 'conn insert done on tester, index 0')
+             > table.insert(ta, '  primary key value = 800.')
+             > wtuple = conn.space.tester:select{800}
+             > table.insert(ta, 'conn select done on tester, index 0')
+             > table.insert(ta, '  number of fields = ' .. #wtuple)
+             > conn.space.tester:delete{800}
+             > table.insert(ta, 'conn delete done on tester')
+             > conn.space.tester:replace{800, 'New data', 'Extra data'}
+             > table.insert(ta, 'conn:replace done on tester')
+             > conn:timeout(0.5).space.tester:update({800}, {{'=', 2, 'Fld#1'}})
+             > table.insert(ta, 'conn update done on tester')
+             > conn:close()
+             > table.insert(ta, 'conn close done')
+             > end!
+    ---
+    ...
+    tarantool> console.delimiter('')!
+    ---
+    ...
+    tarantool> ta = {}
+    ---
+    ...
+    tarantool> example()
+    ---
+    ...
+    tarantool> ta
+    ---
+    - - self:ping() succeeded
+      - '  (no surprise -- self connection is pre-established)'
+      - The local server listen address = 3301
+      - conn delete done on tester.
+      - conn insert done on tester, index 0
+      - '  primary key value = 800.'
+      - conn select done on tester, index 0
+      - '  number of fields = 1'
+      - conn delete done on tester
+      - conn:replace done on tester
+      - conn update done on tester
+      - conn close done
+    ...
+    tarantool> box.space.tester:select{800} -- Prove that the update succeeded.
+    ---
+    - [800, 'Fld#1', 'Extra data']
+    ...
+
diff --git a/doc/sphinx/reference/index.rst b/doc/sphinx/reference/index.rst
index 7782683952061970d7bcfc493969aaeade61abf7..5b7fa521194b04e96a39e4a392e89737b57c8519 100644
--- a/doc/sphinx/reference/index.rst
+++ b/doc/sphinx/reference/index.rst
@@ -19,7 +19,6 @@ Lua functions can run in the background and perform administrative tasks.
     msgpack
     fiber
     fiber-ipc
-    box_session
     socket
     fio
     console