xref: /openbmc/hiomapd/Documentation/mboxd.md (revision f1e547c7)
1Copyright 2017,2018 IBM
2
3Licensed under the Apache License, Version 2.0 (the "License");
4you may not use this file except in compliance with the License.
5You may obtain a copy of the License at
6
7  http://www.apache.org/licenses/LICENSE-2.0
8
9Unless required by applicable law or agreed to in writing, software
10distributed under the License is distributed on an "AS IS" BASIS,
11WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12See the License for the specific language governing permissions and
13limitations under the License.
14
15## Intro
16
17This document describes the reference mailbox daemon contained in this
18repository.
19
20## Files
21
22The main mailbox daemon is implemented in mboxd.c. This file uses helper
23functions from the various mboxd_*.c files.
24
25```
26dbus.c -    Contains the handlers for the D-Bus commands which the daemon can
27                  receive.
28flash.c -   Contains the functions for performing flash access including
29                  read, write and erase.
30lpc.c -     Contains the functions for controlling the LPC bus mapping
31                  including pointing the bus so it maps flash and memory.
32transport_mbox.c -     Contains the handlers for the mbox commands which the daemon
33                  can receive.
34windows.c - Contains the functions for managing the window cache.
35```
36
37## Daemon State
38
39The daemon is a state machine with 5 valid states:
40
41```
42UNINITIALISED -         The daemon is still in the initialisation phase and
43                        will not respond
44ACTIVE_MAPS_FLASH -     The daemon is polling for incoming commands, is not
45                        currently suspended and the LPC bus maps the flash
46                        device.
47SUSPEND_MAPS_FLASH -    The daemon is polling for incoming commands, is
48                        currently suspended and the LPC bus maps the flash
49                        device.
50ACTIVE_MAPS_MEM -       The daemon is polling for incoming commands, is not
51                        currently suspended and the LPC bus maps the reserved
52                        memory region.
53SUSPEND_MAPS_MEM -      The daemon is polling for incoming commands, is
54                        currently suspended and the LPC bus maps the reserved
55                        memory region.
56```
57
58As described in the protocol, the daemon can be suspended to allow the BMC to
59access flash without the daemon interfering. The daemon will still respond to
60commands while suspended but won't allow the host to, or itself, access the
61flash.
62
63### State Transitions
64
65```
66UNINITIALISED -> ACTIVE_MAPS_FLASH -      Uninitiated: Occurs when the daemon is
67                                          finished initialising.
68ACTIVE_MAPS_FLASH -> SUSPEND_MAPS_FLASH - Suspend command received over
69                                          D-Bus
70SUSPEND_MAPS_FLASH -> ACTIVE_MAPS_FLASH - Resume command received over
71                                          D-Bus
72ACTIVE_MAPS_MEM -> SUSPEND_MAPS_MEM -     Suspend command received over D-Bus
73SUSPEND_MAPS_MEM -> ACTIVE_MAPS_MEM -     Resume command received over D-Bus
74ACTIVE_MAPS_FLASH -> ACTIVE_MAPS_MEM -    GET_MBOX_INFO command received
75SUSPEND_MAPS_FLASH -> SUSPEND_MAPS_MEM -  GET_MBOX_INFO command received
76ACTIVE_MAPS_MEM -> ACTIVE_MAPS_FLASH -    Reset D-Bus or mbox command received
77SUSPEND_MAPS_MEM -> SUSPEND_MAPS_FLASH -  Transition not allowed, we
78                                          don't let the host modify flash
79                                          while the daemon is suspended.
80```
81
82## Window Cache
83
84While the protocol describes that there is only one active window at a time,
85the daemon keeps a cache of previously accessed windows to avoid the need to
86reload them from flash should the host access them again in the future.
87
88The reserved memory region is divided among a number of windows which make up
89the window cache. When the host requests a flash offset the cache is searched
90for one which contains that offset. If one is found we simply point the host to
91it at the correct LPC offset for that windows location and the requested flash
92offset.
93
94If there is no window in the cache which contains the requested flash offset
95then we have to find one to load with the requested flash contents. If there
96are any windows which are empty then we choose those, otherwise, we choose one to
97evict using a least recently used (LRU) scheme. The flash is then copied into
98this window and the host pointed at its location on the LPC bus.
99
100When ever the flash is changed we have to invalidate all windows in the window
101cache as their contents may no longer accurately reflect those of the flash.
102
103## Daemon Operation
104
105### Invocation
106
107The daemon is invoked on the command line with a few parameters:
108
109```
110(*) - required
111(#) - optional but recommended
112(~) - optional
113
114--flash *       - The size of the PNOR image on the flash device
115--window-size # - The size to make each window in the cache
116--window-num #  - The number of windows to have in the cache
117--verbose ~     - Increase the verbosity with which the daemon runs
118--sys-log ~     - Use the system log rather than outputting to the console
119```
120
121If any of the required parameters are missing or invalid an error will be
122printed and the daemon will terminate.
123If window-size and window-num aren't specified then the default is to have a
124single window which spans the entire reserved memory region.
125
126### Initialisation
127
128After the command line has been parsed the daemon will initalise its various
129interfaces. If any of these initialisations fail it will print an error and the
130daemon will terminate.
131
132After initilisation, the daemon points the LPC mapping to the actual flash
133device, sets the BMC_READY BMC event and starts polling.
134
135### Polling
136
137The daemon sits in a poll loop waiting for an event to happen on one or more of
138the mbox, D-Bus or signal file descriptors.
139
140#### Handling MBOX Commands
141
142When an event occurs on the mbox file descriptor the mbox request is read from
143the mbox registers and processed.
144
145The command is validated and then the appropriate handler called. The response
146is then written back to the mbox registers to indicate the outcome of the
147command and an interrupt is sent to the host.
148
149#### Handling D-Bus Commands
150
151When an event occurs on the D-Bus file descriptor the D-Bus request is read from
152the D-Bus interface and processed.
153
154The command is validated and then the appropriate handler called. The response
155is then written back to the D-Bus interface to indicate the outcome of the
156command.
157
158#### Handling Signals
159
160The daemon blocks SIGINTs, SIGTERMs, and SIGHUPs and instead polls for them on
161a signal file descriptor.
162
163When an event occurs on this file descriptor the signal received is determined
164and processed as follows:
165
166```
167SIGINT -  Terminate the daemon
168SIGTERM - Terminate the daemon
169SIGHUP -  Clear the window cache and point the LPC bus mapping back to
170          flash
171```
172
173### Termination
174
175The daemon can be terminated for multiple reasons; invalid command line, unable
176to initialise, received SIGINT or SIGTERM, or because it received the kill D-Bus
177command.
178
179On termination, the daemon clears the window cache and notifies the host that the
180active window has been closed, points the LPC bus mapping back to flash, clears
181the BMC_READY BMC event bit and frees all of its allocated resources.
182