xref: /openbmc/qemu/include/hw/resettable.h (revision e10cd93872c31332b002c933a798ab0bc51705a4)
1bc5a39bfSDamien Hedde /*
2bc5a39bfSDamien Hedde  * Resettable interface header.
3bc5a39bfSDamien Hedde  *
4bc5a39bfSDamien Hedde  * Copyright (c) 2019 GreenSocs SAS
5bc5a39bfSDamien Hedde  *
6bc5a39bfSDamien Hedde  * Authors:
7bc5a39bfSDamien Hedde  *   Damien Hedde
8bc5a39bfSDamien Hedde  *
9bc5a39bfSDamien Hedde  * This work is licensed under the terms of the GNU GPL, version 2 or later.
10bc5a39bfSDamien Hedde  * See the COPYING file in the top-level directory.
11bc5a39bfSDamien Hedde  */
12bc5a39bfSDamien Hedde 
13bc5a39bfSDamien Hedde #ifndef HW_RESETTABLE_H
14bc5a39bfSDamien Hedde #define HW_RESETTABLE_H
15bc5a39bfSDamien Hedde 
16bc5a39bfSDamien Hedde #include "qom/object.h"
17bc5a39bfSDamien Hedde 
18bc5a39bfSDamien Hedde #define TYPE_RESETTABLE_INTERFACE "resettable"
19bc5a39bfSDamien Hedde 
20db1015e9SEduardo Habkost typedef struct ResettableClass ResettableClass;
218110fa1dSEduardo Habkost DECLARE_CLASS_CHECKERS(ResettableClass, RESETTABLE,
228110fa1dSEduardo Habkost                        TYPE_RESETTABLE_INTERFACE)
23bc5a39bfSDamien Hedde 
24bc5a39bfSDamien Hedde 
25bc5a39bfSDamien Hedde typedef struct ResettableState ResettableState;
26bc5a39bfSDamien Hedde 
27bc5a39bfSDamien Hedde /**
28bc5a39bfSDamien Hedde  * ResetType:
29bc5a39bfSDamien Hedde  * Types of reset.
30bc5a39bfSDamien Hedde  *
31bc5a39bfSDamien Hedde  * + Cold: reset resulting from a power cycle of the object.
32*759cbb4eSJuraj Marcin  * + Wakeup: reset resulting from a wake-up from a suspended state.
33bc5a39bfSDamien Hedde  *
34bc5a39bfSDamien Hedde  * TODO: Support has to be added to handle more types. In particular,
35bc5a39bfSDamien Hedde  * ResettableState structure needs to be expanded.
36bc5a39bfSDamien Hedde  */
37bc5a39bfSDamien Hedde typedef enum ResetType {
38bc5a39bfSDamien Hedde     RESET_TYPE_COLD,
39631f46d4SPeter Maydell     RESET_TYPE_SNAPSHOT_LOAD,
40*759cbb4eSJuraj Marcin     RESET_TYPE_WAKEUP,
41cf7f61d1SPeter Maydell     RESET_TYPE_S390_CPU_INITIAL,
42cf7f61d1SPeter Maydell     RESET_TYPE_S390_CPU_NORMAL,
43bc5a39bfSDamien Hedde } ResetType;
44bc5a39bfSDamien Hedde 
45bc5a39bfSDamien Hedde /*
46bc5a39bfSDamien Hedde  * ResettableClass:
47bc5a39bfSDamien Hedde  * Interface for resettable objects.
48bc5a39bfSDamien Hedde  *
49bc5a39bfSDamien Hedde  * See docs/devel/reset.rst for more detailed information about how QEMU models
50bc5a39bfSDamien Hedde  * reset. This whole API must only be used when holding the iothread mutex.
51bc5a39bfSDamien Hedde  *
52bc5a39bfSDamien Hedde  * All objects which can be reset must implement this interface;
53bc5a39bfSDamien Hedde  * it is usually provided by a base class such as DeviceClass or BusClass.
54bc5a39bfSDamien Hedde  * Every Resettable object must maintain some state tracking the
55bc5a39bfSDamien Hedde  * progress of a reset operation by providing a ResettableState structure.
56bc5a39bfSDamien Hedde  * The functions defined in this module take care of updating the
57bc5a39bfSDamien Hedde  * state of the reset.
58bc5a39bfSDamien Hedde  * The base class implementation of the interface provides this
59bc5a39bfSDamien Hedde  * state and implements the associated method: get_state.
60bc5a39bfSDamien Hedde  *
61bc5a39bfSDamien Hedde  * Concrete object implementations (typically specific devices
62bc5a39bfSDamien Hedde  * such as a UART model) should provide the functions
63bc5a39bfSDamien Hedde  * for the phases.enter, phases.hold and phases.exit methods, which
64bc5a39bfSDamien Hedde  * they can set in their class init function, either directly or
65bc5a39bfSDamien Hedde  * by calling resettable_class_set_parent_phases().
66bc5a39bfSDamien Hedde  * The phase methods are guaranteed to only only ever be called once
67bc5a39bfSDamien Hedde  * for any reset event, in the order 'enter', 'hold', 'exit'.
68bc5a39bfSDamien Hedde  * An object will always move quickly from 'enter' to 'hold'
69bc5a39bfSDamien Hedde  * but might remain in 'hold' for an arbitrary period of time
70bc5a39bfSDamien Hedde  * before eventually reset is deasserted and the 'exit' phase is called.
71bc5a39bfSDamien Hedde  * Object implementations should be prepared for functions handling
72bc5a39bfSDamien Hedde  * inbound connections from other devices (such as qemu_irq handler
73bc5a39bfSDamien Hedde  * functions) to be called at any point during reset after their
74bc5a39bfSDamien Hedde  * 'enter' method has been called.
75bc5a39bfSDamien Hedde  *
76bc5a39bfSDamien Hedde  * Users of a resettable object should not call these methods
77bc5a39bfSDamien Hedde  * directly, but instead use the function resettable_reset().
78bc5a39bfSDamien Hedde  *
79bc5a39bfSDamien Hedde  * @phases.enter: This phase is called when the object enters reset. It
80bc5a39bfSDamien Hedde  * should reset local state of the object, but it must not do anything that
81bc5a39bfSDamien Hedde  * has a side-effect on other objects, such as raising or lowering a qemu_irq
82bc5a39bfSDamien Hedde  * line or reading or writing guest memory. It takes the reset's type as
83bc5a39bfSDamien Hedde  * argument.
84bc5a39bfSDamien Hedde  *
85bc5a39bfSDamien Hedde  * @phases.hold: This phase is called for entry into reset, once every object
86bc5a39bfSDamien Hedde  * in the system which is being reset has had its @phases.enter method called.
87bc5a39bfSDamien Hedde  * At this point devices can do actions that affect other objects.
88bc5a39bfSDamien Hedde  *
89bc5a39bfSDamien Hedde  * @phases.exit: This phase is called when the object leaves the reset state.
90bc5a39bfSDamien Hedde  * Actions affecting other objects are permitted.
91bc5a39bfSDamien Hedde  *
92bc5a39bfSDamien Hedde  * @get_state: Mandatory method which must return a pointer to a
93bc5a39bfSDamien Hedde  * ResettableState.
94bc5a39bfSDamien Hedde  *
95bc5a39bfSDamien Hedde  * @child_foreach: Executes a given callback on every Resettable child. Child
96bc5a39bfSDamien Hedde  * in this context means a child in the qbus tree, so the children of a qbus
97bc5a39bfSDamien Hedde  * are the devices on it, and the children of a device are all the buses it
98bc5a39bfSDamien Hedde  * owns. This is not the same as the QOM object hierarchy. The function takes
99bc5a39bfSDamien Hedde  * additional opaque and ResetType arguments which must be passed unmodified to
100bc5a39bfSDamien Hedde  * the callback.
101bc5a39bfSDamien Hedde  */
102bc5a39bfSDamien Hedde typedef void (*ResettableEnterPhase)(Object *obj, ResetType type);
103ad80e367SPeter Maydell typedef void (*ResettableHoldPhase)(Object *obj, ResetType type);
104ad80e367SPeter Maydell typedef void (*ResettableExitPhase)(Object *obj, ResetType type);
105bc5a39bfSDamien Hedde typedef ResettableState * (*ResettableGetState)(Object *obj);
106bc5a39bfSDamien Hedde typedef void (*ResettableChildCallback)(Object *, void *opaque,
107bc5a39bfSDamien Hedde                                         ResetType type);
108bc5a39bfSDamien Hedde typedef void (*ResettableChildForeach)(Object *obj,
109bc5a39bfSDamien Hedde                                        ResettableChildCallback cb,
110bc5a39bfSDamien Hedde                                        void *opaque, ResetType type);
111bc5a39bfSDamien Hedde typedef struct ResettablePhases {
112bc5a39bfSDamien Hedde     ResettableEnterPhase enter;
113bc5a39bfSDamien Hedde     ResettableHoldPhase hold;
114bc5a39bfSDamien Hedde     ResettableExitPhase exit;
115bc5a39bfSDamien Hedde } ResettablePhases;
116db1015e9SEduardo Habkost struct ResettableClass {
117bc5a39bfSDamien Hedde     InterfaceClass parent_class;
118bc5a39bfSDamien Hedde 
119bc5a39bfSDamien Hedde     /* Phase methods */
120bc5a39bfSDamien Hedde     ResettablePhases phases;
121bc5a39bfSDamien Hedde 
122bc5a39bfSDamien Hedde     /* State access method */
123bc5a39bfSDamien Hedde     ResettableGetState get_state;
124bc5a39bfSDamien Hedde 
125bc5a39bfSDamien Hedde     /* Hierarchy handling method */
126bc5a39bfSDamien Hedde     ResettableChildForeach child_foreach;
127db1015e9SEduardo Habkost };
128bc5a39bfSDamien Hedde 
129bc5a39bfSDamien Hedde /**
130bc5a39bfSDamien Hedde  * ResettableState:
131bc5a39bfSDamien Hedde  * Structure holding reset related state. The fields should not be accessed
132bc5a39bfSDamien Hedde  * directly; the definition is here to allow further inclusion into other
133bc5a39bfSDamien Hedde  * objects.
134bc5a39bfSDamien Hedde  *
135bc5a39bfSDamien Hedde  * @count: Number of reset level the object is into. It is incremented when
136bc5a39bfSDamien Hedde  * the reset operation starts and decremented when it finishes.
137bc5a39bfSDamien Hedde  * @hold_phase_pending: flag which indicates that we need to invoke the 'hold'
138bc5a39bfSDamien Hedde  * phase handler for this object.
139bc5a39bfSDamien Hedde  * @exit_phase_in_progress: true if we are currently in the exit phase
140bc5a39bfSDamien Hedde  */
141bc5a39bfSDamien Hedde struct ResettableState {
142bc5a39bfSDamien Hedde     unsigned count;
143bc5a39bfSDamien Hedde     bool hold_phase_pending;
144bc5a39bfSDamien Hedde     bool exit_phase_in_progress;
145bc5a39bfSDamien Hedde };
146bc5a39bfSDamien Hedde 
147bc5a39bfSDamien Hedde /**
148e755e127SDamien Hedde  * resettable_state_clear:
149e755e127SDamien Hedde  * Clear the state. It puts the state to the initial (zeroed) state required
150e755e127SDamien Hedde  * to reuse an object. Typically used in realize step of base classes
151e755e127SDamien Hedde  * implementing the interface.
152e755e127SDamien Hedde  */
resettable_state_clear(ResettableState * state)153e755e127SDamien Hedde static inline void resettable_state_clear(ResettableState *state)
154e755e127SDamien Hedde {
155e755e127SDamien Hedde     memset(state, 0, sizeof(ResettableState));
156e755e127SDamien Hedde }
157e755e127SDamien Hedde 
158e755e127SDamien Hedde /**
159bc5a39bfSDamien Hedde  * resettable_reset:
160bc5a39bfSDamien Hedde  * Trigger a reset on an object @obj of type @type. @obj must implement
161bc5a39bfSDamien Hedde  * Resettable interface.
162bc5a39bfSDamien Hedde  *
163bc5a39bfSDamien Hedde  * Calling this function is equivalent to calling @resettable_assert_reset()
164bc5a39bfSDamien Hedde  * then @resettable_release_reset().
165bc5a39bfSDamien Hedde  */
166bc5a39bfSDamien Hedde void resettable_reset(Object *obj, ResetType type);
167bc5a39bfSDamien Hedde 
168bc5a39bfSDamien Hedde /**
169bc5a39bfSDamien Hedde  * resettable_assert_reset:
170bc5a39bfSDamien Hedde  * Put an object @obj into reset. @obj must implement Resettable interface.
171bc5a39bfSDamien Hedde  *
172bc5a39bfSDamien Hedde  * @resettable_release_reset() must eventually be called after this call.
173bc5a39bfSDamien Hedde  * There must be one call to @resettable_release_reset() per call of
174bc5a39bfSDamien Hedde  * @resettable_assert_reset(), with the same type argument.
175bc5a39bfSDamien Hedde  *
176bc5a39bfSDamien Hedde  * NOTE: Until support for migration is added, the @resettable_release_reset()
177bc5a39bfSDamien Hedde  * must not be delayed. It must occur just after @resettable_assert_reset() so
178bc5a39bfSDamien Hedde  * that migration cannot be triggered in between. Prefer using
179bc5a39bfSDamien Hedde  * @resettable_reset() for now.
180bc5a39bfSDamien Hedde  */
181bc5a39bfSDamien Hedde void resettable_assert_reset(Object *obj, ResetType type);
182bc5a39bfSDamien Hedde 
183bc5a39bfSDamien Hedde /**
184bc5a39bfSDamien Hedde  * resettable_release_reset:
185bc5a39bfSDamien Hedde  * Release the object @obj from reset. @obj must implement Resettable interface.
186bc5a39bfSDamien Hedde  *
187bc5a39bfSDamien Hedde  * See @resettable_assert_reset() description for details.
188bc5a39bfSDamien Hedde  */
189bc5a39bfSDamien Hedde void resettable_release_reset(Object *obj, ResetType type);
190bc5a39bfSDamien Hedde 
191bc5a39bfSDamien Hedde /**
192bc5a39bfSDamien Hedde  * resettable_is_in_reset:
193bc5a39bfSDamien Hedde  * Return true if @obj is under reset.
194bc5a39bfSDamien Hedde  *
195bc5a39bfSDamien Hedde  * @obj must implement Resettable interface.
196bc5a39bfSDamien Hedde  */
197bc5a39bfSDamien Hedde bool resettable_is_in_reset(Object *obj);
198bc5a39bfSDamien Hedde 
199bc5a39bfSDamien Hedde /**
200614f731aSDamien Hedde  * resettable_change_parent:
201614f731aSDamien Hedde  * Indicate that the parent of Ressettable @obj is changing from @oldp to @newp.
202614f731aSDamien Hedde  * All 3 objects must implement resettable interface. @oldp or @newp may be
203614f731aSDamien Hedde  * NULL.
204614f731aSDamien Hedde  *
205614f731aSDamien Hedde  * This function will adapt the reset state of @obj so that it is coherent
206614f731aSDamien Hedde  * with the reset state of @newp. It may trigger @resettable_assert_reset()
207614f731aSDamien Hedde  * or @resettable_release_reset(). It will do such things only if the reset
208614f731aSDamien Hedde  * state of @newp and @oldp are different.
209614f731aSDamien Hedde  *
210614f731aSDamien Hedde  * When using this function during reset, it must only be called during
211614f731aSDamien Hedde  * a hold phase method. Calling this during enter or exit phase is an error.
212614f731aSDamien Hedde  */
213614f731aSDamien Hedde void resettable_change_parent(Object *obj, Object *newp, Object *oldp);
214614f731aSDamien Hedde 
215614f731aSDamien Hedde /**
216abb89dbfSDamien Hedde  * resettable_cold_reset_fn:
217abb89dbfSDamien Hedde  * Helper to call resettable_reset((Object *) opaque, RESET_TYPE_COLD).
218abb89dbfSDamien Hedde  *
219abb89dbfSDamien Hedde  * This function is typically useful to register a reset handler with
220abb89dbfSDamien Hedde  * qemu_register_reset.
221abb89dbfSDamien Hedde  */
222abb89dbfSDamien Hedde void resettable_cold_reset_fn(void *opaque);
223abb89dbfSDamien Hedde 
224abb89dbfSDamien Hedde /**
225bc5a39bfSDamien Hedde  * resettable_class_set_parent_phases:
226bc5a39bfSDamien Hedde  *
227bc5a39bfSDamien Hedde  * Save @rc current reset phases into @parent_phases and override @rc phases
228bc5a39bfSDamien Hedde  * by the given new methods (@enter, @hold and @exit).
229bc5a39bfSDamien Hedde  * Each phase is overridden only if the new one is not NULL allowing to
230bc5a39bfSDamien Hedde  * override a subset of phases.
231bc5a39bfSDamien Hedde  */
232bc5a39bfSDamien Hedde void resettable_class_set_parent_phases(ResettableClass *rc,
233bc5a39bfSDamien Hedde                                         ResettableEnterPhase enter,
234bc5a39bfSDamien Hedde                                         ResettableHoldPhase hold,
235bc5a39bfSDamien Hedde                                         ResettableExitPhase exit,
236bc5a39bfSDamien Hedde                                         ResettablePhases *parent_phases);
237bc5a39bfSDamien Hedde 
238bc5a39bfSDamien Hedde #endif
239