1 | /* |
2 | * Copyright 2019 Advanced Micro Devices, Inc. |
3 | * |
4 | * Permission is hereby granted, free of charge, to any person obtaining a |
5 | * copy of this software and associated documentation files (the "Software"), |
6 | * to deal in the Software without restriction, including without limitation |
7 | * the rights to use, copy, modify, merge, publish, distribute, sublicense, |
8 | * and/or sell copies of the Software, and to permit persons to whom the |
9 | * Software is furnished to do so, subject to the following conditions: |
10 | * |
11 | * The above copyright notice and this permission notice shall be included in |
12 | * all copies or substantial portions of the Software. |
13 | * |
14 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR |
15 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, |
16 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL |
17 | * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR |
18 | * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, |
19 | * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR |
20 | * OTHER DEALINGS IN THE SOFTWARE. |
21 | * |
22 | * Authors: AMD |
23 | * |
24 | */ |
25 | |
26 | #ifndef _DMUB_SRV_H_ |
27 | #define _DMUB_SRV_H_ |
28 | |
29 | /** |
30 | * DOC: DMUB interface and operation |
31 | * |
32 | * DMUB is the interface to the display DMCUB microcontroller on DCN hardware. |
33 | * It delegates hardware initialization and command submission to the |
34 | * microcontroller. DMUB is the shortname for DMCUB. |
35 | * |
36 | * This interface is not thread-safe. Ensure that all access to the interface |
37 | * is properly synchronized by the caller. |
38 | * |
39 | * Initialization and usage of the DMUB service should be done in the |
40 | * steps given below: |
41 | * |
42 | * 1. dmub_srv_create() |
43 | * 2. dmub_srv_has_hw_support() |
44 | * 3. dmub_srv_calc_region_info() |
45 | * 4. dmub_srv_hw_init() |
46 | * |
47 | * The call to dmub_srv_create() is required to use the server. |
48 | * |
49 | * The calls to dmub_srv_has_hw_support() and dmub_srv_calc_region_info() |
50 | * are helpers to query cache window size and allocate framebuffer(s) |
51 | * for the cache windows. |
52 | * |
53 | * The call to dmub_srv_hw_init() programs the DMCUB registers to prepare |
54 | * for command submission. Commands can be queued via dmub_srv_cmd_queue() |
55 | * and executed via dmub_srv_cmd_execute(). |
56 | * |
57 | * If the queue is full the dmub_srv_wait_for_idle() call can be used to |
58 | * wait until the queue has been cleared. |
59 | * |
60 | * Destroying the DMUB service can be done by calling dmub_srv_destroy(). |
61 | * This does not clear DMUB hardware state, only software state. |
62 | * |
63 | * The interface is intended to be standalone and should not depend on any |
64 | * other component within DAL. |
65 | */ |
66 | |
67 | #include "inc/dmub_cmd.h" |
68 | #include "dc/dc_types.h" |
69 | |
70 | #if defined(__cplusplus) |
71 | extern "C" { |
72 | #endif |
73 | |
74 | /* Forward declarations */ |
75 | struct dmub_srv; |
76 | struct dmub_srv_common_regs; |
77 | struct dmub_srv_dcn31_regs; |
78 | |
79 | struct dmcub_trace_buf_entry; |
80 | |
81 | /* enum dmub_status - return code for dmcub functions */ |
82 | enum dmub_status { |
83 | DMUB_STATUS_OK = 0, |
84 | DMUB_STATUS_NO_CTX, |
85 | DMUB_STATUS_QUEUE_FULL, |
86 | DMUB_STATUS_TIMEOUT, |
87 | DMUB_STATUS_INVALID, |
88 | DMUB_STATUS_HW_FAILURE, |
89 | }; |
90 | |
91 | /* enum dmub_asic - dmub asic identifier */ |
92 | enum dmub_asic { |
93 | DMUB_ASIC_NONE = 0, |
94 | DMUB_ASIC_DCN20, |
95 | DMUB_ASIC_DCN21, |
96 | DMUB_ASIC_DCN30, |
97 | DMUB_ASIC_DCN301, |
98 | DMUB_ASIC_DCN302, |
99 | DMUB_ASIC_DCN303, |
100 | DMUB_ASIC_DCN31, |
101 | DMUB_ASIC_DCN31B, |
102 | DMUB_ASIC_DCN314, |
103 | DMUB_ASIC_DCN315, |
104 | DMUB_ASIC_DCN316, |
105 | DMUB_ASIC_DCN32, |
106 | DMUB_ASIC_DCN321, |
107 | DMUB_ASIC_DCN35, |
108 | DMUB_ASIC_MAX, |
109 | }; |
110 | |
111 | /* enum dmub_window_id - dmub window identifier */ |
112 | enum dmub_window_id { |
113 | DMUB_WINDOW_0_INST_CONST = 0, |
114 | DMUB_WINDOW_1_STACK, |
115 | DMUB_WINDOW_2_BSS_DATA, |
116 | DMUB_WINDOW_3_VBIOS, |
117 | DMUB_WINDOW_4_MAILBOX, |
118 | DMUB_WINDOW_5_TRACEBUFF, |
119 | DMUB_WINDOW_6_FW_STATE, |
120 | DMUB_WINDOW_7_SCRATCH_MEM, |
121 | DMUB_WINDOW_TOTAL, |
122 | }; |
123 | |
124 | /* enum dmub_notification_type - dmub outbox notification identifier */ |
125 | enum dmub_notification_type { |
126 | DMUB_NOTIFICATION_NO_DATA = 0, |
127 | DMUB_NOTIFICATION_AUX_REPLY, |
128 | DMUB_NOTIFICATION_HPD, |
129 | DMUB_NOTIFICATION_HPD_IRQ, |
130 | DMUB_NOTIFICATION_SET_CONFIG_REPLY, |
131 | DMUB_NOTIFICATION_DPIA_NOTIFICATION, |
132 | DMUB_NOTIFICATION_MAX |
133 | }; |
134 | |
135 | /** |
136 | * DPIA NOTIFICATION Response Type |
137 | */ |
138 | enum dpia_notify_bw_alloc_status { |
139 | |
140 | DPIA_BW_REQ_FAILED = 0, |
141 | DPIA_BW_REQ_SUCCESS, |
142 | DPIA_EST_BW_CHANGED, |
143 | DPIA_BW_ALLOC_CAPS_CHANGED |
144 | }; |
145 | |
146 | /* enum dmub_memory_access_type - memory access method */ |
147 | enum dmub_memory_access_type { |
148 | DMUB_MEMORY_ACCESS_DEFAULT, |
149 | DMUB_MEMORY_ACCESS_CPU = DMUB_MEMORY_ACCESS_DEFAULT, |
150 | DMUB_MEMORY_ACCESS_DMA |
151 | }; |
152 | |
153 | /** |
154 | * struct dmub_region - dmub hw memory region |
155 | * @base: base address for region, must be 256 byte aligned |
156 | * @top: top address for region |
157 | */ |
158 | struct dmub_region { |
159 | uint32_t base; |
160 | uint32_t top; |
161 | }; |
162 | |
163 | /** |
164 | * struct dmub_window - dmub hw cache window |
165 | * @off: offset to the fb memory in gpu address space |
166 | * @r: region in uc address space for cache window |
167 | */ |
168 | struct dmub_window { |
169 | union dmub_addr offset; |
170 | struct dmub_region region; |
171 | }; |
172 | |
173 | /** |
174 | * struct dmub_fb - defines a dmub framebuffer memory region |
175 | * @cpu_addr: cpu virtual address for the region, NULL if invalid |
176 | * @gpu_addr: gpu virtual address for the region, NULL if invalid |
177 | * @size: size of the region in bytes, zero if invalid |
178 | */ |
179 | struct dmub_fb { |
180 | void *cpu_addr; |
181 | uint64_t gpu_addr; |
182 | uint32_t size; |
183 | }; |
184 | |
185 | /** |
186 | * struct dmub_srv_region_params - params used for calculating dmub regions |
187 | * @inst_const_size: size of the fw inst const section |
188 | * @bss_data_size: size of the fw bss data section |
189 | * @vbios_size: size of the vbios data |
190 | * @fw_bss_data: raw firmware bss data section |
191 | */ |
192 | struct dmub_srv_region_params { |
193 | uint32_t inst_const_size; |
194 | uint32_t bss_data_size; |
195 | uint32_t vbios_size; |
196 | const uint8_t *fw_inst_const; |
197 | const uint8_t *fw_bss_data; |
198 | }; |
199 | |
200 | /** |
201 | * struct dmub_srv_region_info - output region info from the dmub service |
202 | * @fb_size: required minimum fb size for all regions, aligned to 4096 bytes |
203 | * @num_regions: number of regions used by the dmub service |
204 | * @regions: region info |
205 | * |
206 | * The regions are aligned such that they can be all placed within the |
207 | * same framebuffer but they can also be placed into different framebuffers. |
208 | * |
209 | * The size of each region can be calculated by the caller: |
210 | * size = reg.top - reg.base |
211 | * |
212 | * Care must be taken when performing custom allocations to ensure that each |
213 | * region base address is 256 byte aligned. |
214 | */ |
215 | struct dmub_srv_region_info { |
216 | uint32_t fb_size; |
217 | uint8_t num_regions; |
218 | struct dmub_region regions[DMUB_WINDOW_TOTAL]; |
219 | }; |
220 | |
221 | /** |
222 | * struct dmub_srv_fb_params - parameters used for driver fb setup |
223 | * @region_info: region info calculated by dmub service |
224 | * @cpu_addr: base cpu address for the framebuffer |
225 | * @gpu_addr: base gpu virtual address for the framebuffer |
226 | */ |
227 | struct dmub_srv_fb_params { |
228 | const struct dmub_srv_region_info *region_info; |
229 | void *cpu_addr; |
230 | uint64_t gpu_addr; |
231 | }; |
232 | |
233 | /** |
234 | * struct dmub_srv_fb_info - output fb info from the dmub service |
235 | * @num_fbs: number of required dmub framebuffers |
236 | * @fbs: fb data for each region |
237 | * |
238 | * Output from the dmub service helper that can be used by the |
239 | * driver to prepare dmub_fb that can be passed into the dmub |
240 | * hw init service. |
241 | * |
242 | * Assumes that all regions are within the same framebuffer |
243 | * and have been setup according to the region_info generated |
244 | * by the dmub service. |
245 | */ |
246 | struct dmub_srv_fb_info { |
247 | uint8_t num_fb; |
248 | struct dmub_fb fb[DMUB_WINDOW_TOTAL]; |
249 | }; |
250 | |
251 | /* |
252 | * struct dmub_srv_hw_params - params for dmub hardware initialization |
253 | * @fb: framebuffer info for each region |
254 | * @fb_base: base of the framebuffer aperture |
255 | * @fb_offset: offset of the framebuffer aperture |
256 | * @psp_version: psp version to pass for DMCU init |
257 | * @load_inst_const: true if DMUB should load inst const fw |
258 | */ |
259 | struct dmub_srv_hw_params { |
260 | struct dmub_fb *fb[DMUB_WINDOW_TOTAL]; |
261 | uint64_t fb_base; |
262 | uint64_t fb_offset; |
263 | uint32_t psp_version; |
264 | bool load_inst_const; |
265 | bool skip_panel_power_sequence; |
266 | bool disable_z10; |
267 | bool power_optimization; |
268 | bool dpia_supported; |
269 | bool disable_dpia; |
270 | bool usb4_cm_version; |
271 | bool fw_in_system_memory; |
272 | bool dpia_hpd_int_enable_supported; |
273 | bool disable_clock_gate; |
274 | bool disallow_dispclk_dppclk_ds; |
275 | enum dmub_memory_access_type mem_access_type; |
276 | enum dmub_ips_disable_type disable_ips; |
277 | }; |
278 | |
279 | /** |
280 | * struct dmub_diagnostic_data - Diagnostic data retrieved from DMCUB for |
281 | * debugging purposes, including logging, crash analysis, etc. |
282 | */ |
283 | struct dmub_diagnostic_data { |
284 | uint32_t dmcub_version; |
285 | uint32_t scratch[17]; |
286 | uint32_t pc; |
287 | uint32_t undefined_address_fault_addr; |
288 | uint32_t inst_fetch_fault_addr; |
289 | uint32_t data_write_fault_addr; |
290 | uint32_t inbox1_rptr; |
291 | uint32_t inbox1_wptr; |
292 | uint32_t inbox1_size; |
293 | uint32_t inbox0_rptr; |
294 | uint32_t inbox0_wptr; |
295 | uint32_t inbox0_size; |
296 | uint32_t gpint_datain0; |
297 | uint8_t is_dmcub_enabled : 1; |
298 | uint8_t is_dmcub_soft_reset : 1; |
299 | uint8_t is_dmcub_secure_reset : 1; |
300 | uint8_t is_traceport_en : 1; |
301 | uint8_t is_cw0_enabled : 1; |
302 | uint8_t is_cw6_enabled : 1; |
303 | }; |
304 | |
305 | /** |
306 | * struct dmub_srv_base_funcs - Driver specific base callbacks |
307 | */ |
308 | struct dmub_srv_base_funcs { |
309 | /** |
310 | * @reg_read: |
311 | * |
312 | * Hook for reading a register. |
313 | * |
314 | * Return: The 32-bit register value from the given address. |
315 | */ |
316 | uint32_t (*reg_read)(void *ctx, uint32_t address); |
317 | |
318 | /** |
319 | * @reg_write: |
320 | * |
321 | * Hook for writing a value to the register specified by address. |
322 | */ |
323 | void (*reg_write)(void *ctx, uint32_t address, uint32_t value); |
324 | }; |
325 | |
326 | /** |
327 | * struct dmub_srv_hw_funcs - hardware sequencer funcs for dmub |
328 | */ |
329 | struct dmub_srv_hw_funcs { |
330 | /* private: internal use only */ |
331 | |
332 | void (*init)(struct dmub_srv *dmub); |
333 | |
334 | void (*reset)(struct dmub_srv *dmub); |
335 | |
336 | void (*reset_release)(struct dmub_srv *dmub); |
337 | |
338 | void (*backdoor_load)(struct dmub_srv *dmub, |
339 | const struct dmub_window *cw0, |
340 | const struct dmub_window *cw1); |
341 | |
342 | void (*backdoor_load_zfb_mode)(struct dmub_srv *dmub, |
343 | const struct dmub_window *cw0, |
344 | const struct dmub_window *cw1); |
345 | void (*setup_windows)(struct dmub_srv *dmub, |
346 | const struct dmub_window *cw2, |
347 | const struct dmub_window *cw3, |
348 | const struct dmub_window *cw4, |
349 | const struct dmub_window *cw5, |
350 | const struct dmub_window *cw6); |
351 | |
352 | void (*setup_mailbox)(struct dmub_srv *dmub, |
353 | const struct dmub_region *inbox1); |
354 | |
355 | uint32_t (*get_inbox1_wptr)(struct dmub_srv *dmub); |
356 | |
357 | uint32_t (*get_inbox1_rptr)(struct dmub_srv *dmub); |
358 | |
359 | void (*set_inbox1_wptr)(struct dmub_srv *dmub, uint32_t wptr_offset); |
360 | |
361 | void (*setup_out_mailbox)(struct dmub_srv *dmub, |
362 | const struct dmub_region *outbox1); |
363 | |
364 | uint32_t (*get_outbox1_wptr)(struct dmub_srv *dmub); |
365 | |
366 | void (*set_outbox1_rptr)(struct dmub_srv *dmub, uint32_t rptr_offset); |
367 | |
368 | void (*setup_outbox0)(struct dmub_srv *dmub, |
369 | const struct dmub_region *outbox0); |
370 | |
371 | uint32_t (*get_outbox0_wptr)(struct dmub_srv *dmub); |
372 | |
373 | void (*set_outbox0_rptr)(struct dmub_srv *dmub, uint32_t rptr_offset); |
374 | |
375 | uint32_t (*emul_get_inbox1_rptr)(struct dmub_srv *dmub); |
376 | |
377 | void (*emul_set_inbox1_wptr)(struct dmub_srv *dmub, uint32_t wptr_offset); |
378 | |
379 | bool (*is_supported)(struct dmub_srv *dmub); |
380 | |
381 | bool (*is_psrsu_supported)(struct dmub_srv *dmub); |
382 | |
383 | bool (*is_hw_init)(struct dmub_srv *dmub); |
384 | bool (*is_hw_powered_up)(struct dmub_srv *dmub); |
385 | |
386 | void (*enable_dmub_boot_options)(struct dmub_srv *dmub, |
387 | const struct dmub_srv_hw_params *params); |
388 | |
389 | void (*skip_dmub_panel_power_sequence)(struct dmub_srv *dmub, bool skip); |
390 | |
391 | union dmub_fw_boot_status (*get_fw_status)(struct dmub_srv *dmub); |
392 | |
393 | union dmub_fw_boot_options (*get_fw_boot_option)(struct dmub_srv *dmub); |
394 | |
395 | void (*set_gpint)(struct dmub_srv *dmub, |
396 | union dmub_gpint_data_register reg); |
397 | |
398 | bool (*is_gpint_acked)(struct dmub_srv *dmub, |
399 | union dmub_gpint_data_register reg); |
400 | |
401 | uint32_t (*get_gpint_response)(struct dmub_srv *dmub); |
402 | |
403 | uint32_t (*get_gpint_dataout)(struct dmub_srv *dmub); |
404 | |
405 | void (*configure_dmub_in_system_memory)(struct dmub_srv *dmub); |
406 | void (*clear_inbox0_ack_register)(struct dmub_srv *dmub); |
407 | uint32_t (*read_inbox0_ack_register)(struct dmub_srv *dmub); |
408 | void (*send_inbox0_cmd)(struct dmub_srv *dmub, union dmub_inbox0_data_register data); |
409 | uint32_t (*get_current_time)(struct dmub_srv *dmub); |
410 | |
411 | void (*get_diagnostic_data)(struct dmub_srv *dmub, struct dmub_diagnostic_data *dmub_oca); |
412 | |
413 | bool (*should_detect)(struct dmub_srv *dmub); |
414 | void (*init_reg_offsets)(struct dmub_srv *dmub, struct dc_context *ctx); |
415 | |
416 | void (*subvp_save_surf_addr)(struct dmub_srv *dmub, const struct dc_plane_address *addr, uint8_t subvp_index); |
417 | }; |
418 | |
419 | /** |
420 | * struct dmub_srv_create_params - params for dmub service creation |
421 | * @base_funcs: driver supplied base routines |
422 | * @hw_funcs: optional overrides for hw funcs |
423 | * @user_ctx: context data for callback funcs |
424 | * @asic: driver supplied asic |
425 | * @fw_version: the current firmware version, if any |
426 | * @is_virtual: false for hw support only |
427 | */ |
428 | struct dmub_srv_create_params { |
429 | struct dmub_srv_base_funcs funcs; |
430 | struct dmub_srv_hw_funcs *hw_funcs; |
431 | void *user_ctx; |
432 | struct dc_context *dc_ctx; |
433 | enum dmub_asic asic; |
434 | uint32_t fw_version; |
435 | bool is_virtual; |
436 | }; |
437 | |
438 | /** |
439 | * struct dmub_srv - software state for dmcub |
440 | * @asic: dmub asic identifier |
441 | * @user_ctx: user provided context for the dmub_srv |
442 | * @fw_version: the current firmware version, if any |
443 | * @is_virtual: false if hardware support only |
444 | * @fw_state: dmub firmware state pointer |
445 | */ |
446 | struct dmub_srv { |
447 | enum dmub_asic asic; |
448 | void *user_ctx; |
449 | uint32_t fw_version; |
450 | bool is_virtual; |
451 | struct dmub_fb scratch_mem_fb; |
452 | volatile const struct dmub_fw_state *fw_state; |
453 | |
454 | /* private: internal use only */ |
455 | const struct dmub_srv_common_regs *regs; |
456 | const struct dmub_srv_dcn31_regs *regs_dcn31; |
457 | struct dmub_srv_dcn32_regs *regs_dcn32; |
458 | struct dmub_srv_dcn35_regs *regs_dcn35; |
459 | |
460 | struct dmub_srv_base_funcs funcs; |
461 | struct dmub_srv_hw_funcs hw_funcs; |
462 | struct dmub_rb inbox1_rb; |
463 | uint32_t inbox1_last_wptr; |
464 | /** |
465 | * outbox1_rb is accessed without locks (dal & dc) |
466 | * and to be used only in dmub_srv_stat_get_notification() |
467 | */ |
468 | struct dmub_rb outbox1_rb; |
469 | |
470 | struct dmub_rb outbox0_rb; |
471 | |
472 | bool sw_init; |
473 | bool hw_init; |
474 | |
475 | uint64_t fb_base; |
476 | uint64_t fb_offset; |
477 | uint32_t psp_version; |
478 | |
479 | /* Feature capabilities reported by fw */ |
480 | struct dmub_feature_caps feature_caps; |
481 | struct dmub_visual_confirm_color visual_confirm_color; |
482 | }; |
483 | |
484 | /** |
485 | * struct dmub_notification - dmub notification data |
486 | * @type: dmub notification type |
487 | * @link_index: link index to identify aux connection |
488 | * @result: USB4 status returned from dmub |
489 | * @pending_notification: Indicates there are other pending notifications |
490 | * @aux_reply: aux reply |
491 | * @hpd_status: hpd status |
492 | * @bw_alloc_reply: BW Allocation reply from CM/DPIA |
493 | */ |
494 | struct dmub_notification { |
495 | enum dmub_notification_type type; |
496 | uint8_t link_index; |
497 | uint8_t result; |
498 | bool pending_notification; |
499 | union { |
500 | struct aux_reply_data aux_reply; |
501 | enum dp_hpd_status hpd_status; |
502 | enum set_config_status sc_status; |
503 | /** |
504 | * DPIA notification command. |
505 | */ |
506 | struct dmub_rb_cmd_dpia_notification dpia_notification; |
507 | }; |
508 | }; |
509 | |
510 | /** |
511 | * DMUB firmware version helper macro - useful for checking if the version |
512 | * of a firmware to know if feature or functionality is supported or present. |
513 | */ |
514 | #define DMUB_FW_VERSION(major, minor, revision) \ |
515 | ((((major) & 0xFF) << 24) | (((minor) & 0xFF) << 16) | (((revision) & 0xFF) << 8)) |
516 | |
517 | /** |
518 | * dmub_srv_create() - creates the DMUB service. |
519 | * @dmub: the dmub service |
520 | * @params: creation parameters for the service |
521 | * |
522 | * Return: |
523 | * DMUB_STATUS_OK - success |
524 | * DMUB_STATUS_INVALID - unspecified error |
525 | */ |
526 | enum dmub_status dmub_srv_create(struct dmub_srv *dmub, |
527 | const struct dmub_srv_create_params *params); |
528 | |
529 | /** |
530 | * dmub_srv_destroy() - destroys the DMUB service. |
531 | * @dmub: the dmub service |
532 | */ |
533 | void dmub_srv_destroy(struct dmub_srv *dmub); |
534 | |
535 | /** |
536 | * dmub_srv_calc_region_info() - retreives region info from the dmub service |
537 | * @dmub: the dmub service |
538 | * @params: parameters used to calculate region locations |
539 | * @info_out: the output region info from dmub |
540 | * |
541 | * Calculates the base and top address for all relevant dmub regions |
542 | * using the parameters given (if any). |
543 | * |
544 | * Return: |
545 | * DMUB_STATUS_OK - success |
546 | * DMUB_STATUS_INVALID - unspecified error |
547 | */ |
548 | enum dmub_status |
549 | dmub_srv_calc_region_info(struct dmub_srv *dmub, |
550 | const struct dmub_srv_region_params *params, |
551 | struct dmub_srv_region_info *out); |
552 | |
553 | /** |
554 | * dmub_srv_calc_region_info() - retreives fb info from the dmub service |
555 | * @dmub: the dmub service |
556 | * @params: parameters used to calculate fb locations |
557 | * @info_out: the output fb info from dmub |
558 | * |
559 | * Calculates the base and top address for all relevant dmub regions |
560 | * using the parameters given (if any). |
561 | * |
562 | * Return: |
563 | * DMUB_STATUS_OK - success |
564 | * DMUB_STATUS_INVALID - unspecified error |
565 | */ |
566 | enum dmub_status dmub_srv_calc_fb_info(struct dmub_srv *dmub, |
567 | const struct dmub_srv_fb_params *params, |
568 | struct dmub_srv_fb_info *out); |
569 | |
570 | /** |
571 | * dmub_srv_has_hw_support() - returns hw support state for dmcub |
572 | * @dmub: the dmub service |
573 | * @is_supported: hw support state |
574 | * |
575 | * Queries the hardware for DMCUB support and returns the result. |
576 | * |
577 | * Can be called before dmub_srv_hw_init(). |
578 | * |
579 | * Return: |
580 | * DMUB_STATUS_OK - success |
581 | * DMUB_STATUS_INVALID - unspecified error |
582 | */ |
583 | enum dmub_status dmub_srv_has_hw_support(struct dmub_srv *dmub, |
584 | bool *is_supported); |
585 | |
586 | /** |
587 | * dmub_srv_is_hw_init() - returns hardware init state |
588 | * |
589 | * Return: |
590 | * DMUB_STATUS_OK - success |
591 | * DMUB_STATUS_INVALID - unspecified error |
592 | */ |
593 | enum dmub_status dmub_srv_is_hw_init(struct dmub_srv *dmub, bool *is_hw_init); |
594 | |
595 | /** |
596 | * dmub_srv_hw_init() - initializes the underlying DMUB hardware |
597 | * @dmub: the dmub service |
598 | * @params: params for hardware initialization |
599 | * |
600 | * Resets the DMUB hardware and performs backdoor loading of the |
601 | * required cache regions based on the input framebuffer regions. |
602 | * |
603 | * Return: |
604 | * DMUB_STATUS_OK - success |
605 | * DMUB_STATUS_NO_CTX - dmcub context not initialized |
606 | * DMUB_STATUS_INVALID - unspecified error |
607 | */ |
608 | enum dmub_status dmub_srv_hw_init(struct dmub_srv *dmub, |
609 | const struct dmub_srv_hw_params *params); |
610 | |
611 | /** |
612 | * dmub_srv_hw_reset() - puts the DMUB hardware in reset state if initialized |
613 | * @dmub: the dmub service |
614 | * |
615 | * Before destroying the DMUB service or releasing the backing framebuffer |
616 | * memory we'll need to put the DMCUB into reset first. |
617 | * |
618 | * A subsequent call to dmub_srv_hw_init() will re-enable the DMCUB. |
619 | * |
620 | * Return: |
621 | * DMUB_STATUS_OK - success |
622 | * DMUB_STATUS_INVALID - unspecified error |
623 | */ |
624 | enum dmub_status dmub_srv_hw_reset(struct dmub_srv *dmub); |
625 | |
626 | /** |
627 | * dmub_srv_sync_inbox1() - sync sw state with hw state |
628 | * @dmub: the dmub service |
629 | * |
630 | * Sync sw state with hw state when resume from S0i3 |
631 | * |
632 | * Return: |
633 | * DMUB_STATUS_OK - success |
634 | * DMUB_STATUS_INVALID - unspecified error |
635 | */ |
636 | enum dmub_status dmub_srv_sync_inbox1(struct dmub_srv *dmub); |
637 | |
638 | /** |
639 | * dmub_srv_cmd_queue() - queues a command to the DMUB |
640 | * @dmub: the dmub service |
641 | * @cmd: the command to queue |
642 | * |
643 | * Queues a command to the DMUB service but does not begin execution |
644 | * immediately. |
645 | * |
646 | * Return: |
647 | * DMUB_STATUS_OK - success |
648 | * DMUB_STATUS_QUEUE_FULL - no remaining room in queue |
649 | * DMUB_STATUS_INVALID - unspecified error |
650 | */ |
651 | enum dmub_status dmub_srv_cmd_queue(struct dmub_srv *dmub, |
652 | const union dmub_rb_cmd *cmd); |
653 | |
654 | /** |
655 | * dmub_srv_cmd_execute() - Executes a queued sequence to the dmub |
656 | * @dmub: the dmub service |
657 | * |
658 | * Begins execution of queued commands on the dmub. |
659 | * |
660 | * Return: |
661 | * DMUB_STATUS_OK - success |
662 | * DMUB_STATUS_INVALID - unspecified error |
663 | */ |
664 | enum dmub_status dmub_srv_cmd_execute(struct dmub_srv *dmub); |
665 | |
666 | /** |
667 | * dmub_srv_wait_for_hw_pwr_up() - Waits for firmware hardware power up is completed |
668 | * @dmub: the dmub service |
669 | * @timeout_us: the maximum number of microseconds to wait |
670 | * |
671 | * Waits until firmware hardware is powered up. The maximum |
672 | * wait time is given in microseconds to prevent spinning forever. |
673 | * |
674 | * Return: |
675 | * DMUB_STATUS_OK - success |
676 | * DMUB_STATUS_TIMEOUT - timed out |
677 | * DMUB_STATUS_INVALID - unspecified error |
678 | */ |
679 | enum dmub_status dmub_srv_wait_for_hw_pwr_up(struct dmub_srv *dmub, |
680 | uint32_t timeout_us); |
681 | |
682 | bool dmub_srv_is_hw_pwr_up(struct dmub_srv *dmub); |
683 | |
684 | /** |
685 | * dmub_srv_wait_for_auto_load() - Waits for firmware auto load to complete |
686 | * @dmub: the dmub service |
687 | * @timeout_us: the maximum number of microseconds to wait |
688 | * |
689 | * Waits until firmware has been autoloaded by the DMCUB. The maximum |
690 | * wait time is given in microseconds to prevent spinning forever. |
691 | * |
692 | * On ASICs without firmware autoload support this function will return |
693 | * immediately. |
694 | * |
695 | * Return: |
696 | * DMUB_STATUS_OK - success |
697 | * DMUB_STATUS_TIMEOUT - wait for phy init timed out |
698 | * DMUB_STATUS_INVALID - unspecified error |
699 | */ |
700 | enum dmub_status dmub_srv_wait_for_auto_load(struct dmub_srv *dmub, |
701 | uint32_t timeout_us); |
702 | |
703 | /** |
704 | * dmub_srv_wait_for_phy_init() - Waits for DMUB PHY init to complete |
705 | * @dmub: the dmub service |
706 | * @timeout_us: the maximum number of microseconds to wait |
707 | * |
708 | * Waits until the PHY has been initialized by the DMUB. The maximum |
709 | * wait time is given in microseconds to prevent spinning forever. |
710 | * |
711 | * On ASICs without PHY init support this function will return |
712 | * immediately. |
713 | * |
714 | * Return: |
715 | * DMUB_STATUS_OK - success |
716 | * DMUB_STATUS_TIMEOUT - wait for phy init timed out |
717 | * DMUB_STATUS_INVALID - unspecified error |
718 | */ |
719 | enum dmub_status dmub_srv_wait_for_phy_init(struct dmub_srv *dmub, |
720 | uint32_t timeout_us); |
721 | |
722 | /** |
723 | * dmub_srv_wait_for_idle() - Waits for the DMUB to be idle |
724 | * @dmub: the dmub service |
725 | * @timeout_us: the maximum number of microseconds to wait |
726 | * |
727 | * Waits until the DMUB buffer is empty and all commands have |
728 | * finished processing. The maximum wait time is given in |
729 | * microseconds to prevent spinning forever. |
730 | * |
731 | * Return: |
732 | * DMUB_STATUS_OK - success |
733 | * DMUB_STATUS_TIMEOUT - wait for buffer to flush timed out |
734 | * DMUB_STATUS_INVALID - unspecified error |
735 | */ |
736 | enum dmub_status dmub_srv_wait_for_idle(struct dmub_srv *dmub, |
737 | uint32_t timeout_us); |
738 | |
739 | /** |
740 | * dmub_srv_send_gpint_command() - Sends a GPINT based command. |
741 | * @dmub: the dmub service |
742 | * @command_code: the command code to send |
743 | * @param: the command parameter to send |
744 | * @timeout_us: the maximum number of microseconds to wait |
745 | * |
746 | * Sends a command via the general purpose interrupt (GPINT). |
747 | * Waits for the number of microseconds specified by timeout_us |
748 | * for the command ACK before returning. |
749 | * |
750 | * Can be called after software initialization. |
751 | * |
752 | * Return: |
753 | * DMUB_STATUS_OK - success |
754 | * DMUB_STATUS_TIMEOUT - wait for ACK timed out |
755 | * DMUB_STATUS_INVALID - unspecified error |
756 | */ |
757 | enum dmub_status |
758 | dmub_srv_send_gpint_command(struct dmub_srv *dmub, |
759 | enum dmub_gpint_command command_code, |
760 | uint16_t param, uint32_t timeout_us); |
761 | |
762 | /** |
763 | * dmub_srv_get_gpint_response() - Queries the GPINT response. |
764 | * @dmub: the dmub service |
765 | * @response: the response for the last GPINT |
766 | * |
767 | * Returns the response code for the last GPINT interrupt. |
768 | * |
769 | * Can be called after software initialization. |
770 | * |
771 | * Return: |
772 | * DMUB_STATUS_OK - success |
773 | * DMUB_STATUS_INVALID - unspecified error |
774 | */ |
775 | enum dmub_status dmub_srv_get_gpint_response(struct dmub_srv *dmub, |
776 | uint32_t *response); |
777 | |
778 | /** |
779 | * dmub_srv_get_gpint_dataout() - Queries the GPINT DATAOUT. |
780 | * @dmub: the dmub service |
781 | * @dataout: the data for the GPINT DATAOUT |
782 | * |
783 | * Returns the response code for the last GPINT DATAOUT interrupt. |
784 | * |
785 | * Can be called after software initialization. |
786 | * |
787 | * Return: |
788 | * DMUB_STATUS_OK - success |
789 | * DMUB_STATUS_INVALID - unspecified error |
790 | */ |
791 | enum dmub_status dmub_srv_get_gpint_dataout(struct dmub_srv *dmub, |
792 | uint32_t *dataout); |
793 | |
794 | /** |
795 | * dmub_flush_buffer_mem() - Read back entire frame buffer region. |
796 | * This ensures that the write from x86 has been flushed and will not |
797 | * hang the DMCUB. |
798 | * @fb: frame buffer to flush |
799 | * |
800 | * Can be called after software initialization. |
801 | */ |
802 | void dmub_flush_buffer_mem(const struct dmub_fb *fb); |
803 | |
804 | /** |
805 | * dmub_srv_get_fw_boot_status() - Returns the DMUB boot status bits. |
806 | * |
807 | * @dmub: the dmub service |
808 | * @status: out pointer for firmware status |
809 | * |
810 | * Return: |
811 | * DMUB_STATUS_OK - success |
812 | * DMUB_STATUS_INVALID - unspecified error, unsupported |
813 | */ |
814 | enum dmub_status dmub_srv_get_fw_boot_status(struct dmub_srv *dmub, |
815 | union dmub_fw_boot_status *status); |
816 | |
817 | enum dmub_status dmub_srv_get_fw_boot_option(struct dmub_srv *dmub, |
818 | union dmub_fw_boot_options *option); |
819 | |
820 | enum dmub_status dmub_srv_cmd_with_reply_data(struct dmub_srv *dmub, |
821 | union dmub_rb_cmd *cmd); |
822 | |
823 | enum dmub_status dmub_srv_set_skip_panel_power_sequence(struct dmub_srv *dmub, |
824 | bool skip); |
825 | |
826 | bool dmub_srv_get_outbox0_msg(struct dmub_srv *dmub, struct dmcub_trace_buf_entry *entry); |
827 | |
828 | bool dmub_srv_get_diagnostic_data(struct dmub_srv *dmub, struct dmub_diagnostic_data *diag_data); |
829 | |
830 | bool dmub_srv_should_detect(struct dmub_srv *dmub); |
831 | |
832 | /** |
833 | * dmub_srv_send_inbox0_cmd() - Send command to DMUB using INBOX0 |
834 | * @dmub: the dmub service |
835 | * @data: the data to be sent in the INBOX0 command |
836 | * |
837 | * Send command by writing directly to INBOX0 WPTR |
838 | * |
839 | * Return: |
840 | * DMUB_STATUS_OK - success |
841 | * DMUB_STATUS_INVALID - hw_init false or hw function does not exist |
842 | */ |
843 | enum dmub_status dmub_srv_send_inbox0_cmd(struct dmub_srv *dmub, union dmub_inbox0_data_register data); |
844 | |
845 | /** |
846 | * dmub_srv_wait_for_inbox0_ack() - wait for DMUB to ACK INBOX0 command |
847 | * @dmub: the dmub service |
848 | * @timeout_us: the maximum number of microseconds to wait |
849 | * |
850 | * Wait for DMUB to ACK the INBOX0 message |
851 | * |
852 | * Return: |
853 | * DMUB_STATUS_OK - success |
854 | * DMUB_STATUS_INVALID - hw_init false or hw function does not exist |
855 | * DMUB_STATUS_TIMEOUT - wait for ack timed out |
856 | */ |
857 | enum dmub_status dmub_srv_wait_for_inbox0_ack(struct dmub_srv *dmub, uint32_t timeout_us); |
858 | |
859 | /** |
860 | * dmub_srv_wait_for_inbox0_ack() - clear ACK register for INBOX0 |
861 | * @dmub: the dmub service |
862 | * |
863 | * Clear ACK register for INBOX0 |
864 | * |
865 | * Return: |
866 | * DMUB_STATUS_OK - success |
867 | * DMUB_STATUS_INVALID - hw_init false or hw function does not exist |
868 | */ |
869 | enum dmub_status dmub_srv_clear_inbox0_ack(struct dmub_srv *dmub); |
870 | |
871 | /** |
872 | * dmub_srv_subvp_save_surf_addr() - Save primary and meta address for subvp on each flip |
873 | * @dmub: The dmub service |
874 | * @addr: The surface address to be programmed on the current flip |
875 | * @subvp_index: Index of subvp pipe, indicates which subvp pipe the address should be saved for |
876 | * |
877 | * Function to save the surface flip addr into scratch registers. This is to fix a race condition |
878 | * between FW and driver reading / writing to the surface address at the same time. This is |
879 | * required because there is no EARLIEST_IN_USE_META. |
880 | * |
881 | * Return: |
882 | * void |
883 | */ |
884 | void dmub_srv_subvp_save_surf_addr(struct dmub_srv *dmub, const struct dc_plane_address *addr, uint8_t subvp_index); |
885 | |
886 | #if defined(__cplusplus) |
887 | } |
888 | #endif |
889 | |
890 | #endif /* _DMUB_SRV_H_ */ |
891 | |