blob: f8cdb8875d896340e50d58befd90ed0475d312aa [file] [log] [blame]
Chunming Zhoud03846a2015-07-28 14:20:03 -04001/*
2 * Copyright 2015 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 *
23 */
24#ifndef _CGS_COMMON_H
25#define _CGS_COMMON_H
26
27/**
28 * enum cgs_gpu_mem_type - GPU memory types
29 */
30enum cgs_gpu_mem_type {
31 CGS_GPU_MEM_TYPE__VISIBLE_FB,
32 CGS_GPU_MEM_TYPE__INVISIBLE_FB,
33 CGS_GPU_MEM_TYPE__VISIBLE_CONTIG_FB,
34 CGS_GPU_MEM_TYPE__INVISIBLE_CONTIG_FB,
35 CGS_GPU_MEM_TYPE__GART_CACHEABLE,
36 CGS_GPU_MEM_TYPE__GART_WRITECOMBINE
37};
38
39/**
40 * enum cgs_ind_reg - Indirect register spaces
41 */
42enum cgs_ind_reg {
43 CGS_IND_REG__MMIO,
44 CGS_IND_REG__PCIE,
45 CGS_IND_REG__SMC,
46 CGS_IND_REG__UVD_CTX,
47 CGS_IND_REG__DIDT,
48 CGS_IND_REG__AUDIO_ENDPT
49};
50
51/**
52 * enum cgs_clock - Clocks controlled by the SMU
53 */
54enum cgs_clock {
55 CGS_CLOCK__SCLK,
56 CGS_CLOCK__MCLK,
57 CGS_CLOCK__VCLK,
58 CGS_CLOCK__DCLK,
59 CGS_CLOCK__ECLK,
60 CGS_CLOCK__ACLK,
61 CGS_CLOCK__ICLK,
62 /* ... */
63};
64
65/**
66 * enum cgs_engine - Engines that can be statically power-gated
67 */
68enum cgs_engine {
69 CGS_ENGINE__UVD,
70 CGS_ENGINE__VCE,
71 CGS_ENGINE__VP8,
72 CGS_ENGINE__ACP_DMA,
73 CGS_ENGINE__ACP_DSP0,
74 CGS_ENGINE__ACP_DSP1,
75 CGS_ENGINE__ISP,
76 /* ... */
77};
78
79/**
80 * enum cgs_voltage_planes - Voltage planes for external camera HW
81 */
82enum cgs_voltage_planes {
83 CGS_VOLTAGE_PLANE__SENSOR0,
84 CGS_VOLTAGE_PLANE__SENSOR1,
85 /* ... */
86};
87
88/**
89 * struct cgs_clock_limits - Clock limits
90 *
91 * Clocks are specified in 10KHz units.
92 */
93struct cgs_clock_limits {
94 unsigned min; /**< Minimum supported frequency */
95 unsigned max; /**< Maxumim supported frequency */
96 unsigned sustainable; /**< Thermally sustainable frequency */
97};
98
99typedef unsigned long cgs_handle_t;
100
101/**
102 * cgs_gpu_mem_info() - Return information about memory heaps
103 * @cgs_device: opaque device handle
104 * @type: memory type
105 * @mc_start: Start MC address of the heap (output)
106 * @mc_size: MC address space size (output)
107 * @mem_size: maximum amount of memory available for allocation (output)
108 *
109 * This function returns information about memory heaps. The type
110 * parameter is used to select the memory heap. The mc_start and
111 * mc_size for GART heaps may be bigger than the memory available for
112 * allocation.
113 *
114 * mc_start and mc_size are undefined for non-contiguous FB memory
115 * types, since buffers allocated with these types may or may not be
116 * GART mapped.
117 *
118 * Return: 0 on success, -errno otherwise
119 */
120typedef int (*cgs_gpu_mem_info_t)(void *cgs_device, enum cgs_gpu_mem_type type,
121 uint64_t *mc_start, uint64_t *mc_size,
122 uint64_t *mem_size);
123
124/**
125 * cgs_gmap_kmem() - map kernel memory to GART aperture
126 * @cgs_device: opaque device handle
127 * @kmem: pointer to kernel memory
128 * @size: size to map
129 * @min_offset: minimum offset from start of GART aperture
130 * @max_offset: maximum offset from start of GART aperture
131 * @kmem_handle: kernel memory handle (output)
132 * @mcaddr: MC address (output)
133 *
134 * Return: 0 on success, -errno otherwise
135 */
136typedef int (*cgs_gmap_kmem_t)(void *cgs_device, void *kmem, uint64_t size,
137 uint64_t min_offset, uint64_t max_offset,
138 cgs_handle_t *kmem_handle, uint64_t *mcaddr);
139
140/**
141 * cgs_gunmap_kmem() - unmap kernel memory
142 * @cgs_device: opaque device handle
143 * @kmem_handle: kernel memory handle returned by gmap_kmem
144 *
145 * Return: 0 on success, -errno otherwise
146 */
147typedef int (*cgs_gunmap_kmem_t)(void *cgs_device, cgs_handle_t kmem_handle);
148
149/**
150 * cgs_alloc_gpu_mem() - Allocate GPU memory
151 * @cgs_device: opaque device handle
152 * @type: memory type
153 * @size: size in bytes
154 * @align: alignment in bytes
155 * @min_offset: minimum offset from start of heap
156 * @max_offset: maximum offset from start of heap
157 * @handle: memory handle (output)
158 *
159 * The memory types CGS_GPU_MEM_TYPE_*_CONTIG_FB force contiguous
160 * memory allocation. This guarantees that the MC address returned by
161 * cgs_gmap_gpu_mem is not mapped through the GART. The non-contiguous
162 * FB memory types may be GART mapped depending on memory
163 * fragmentation and memory allocator policies.
164 *
165 * If min/max_offset are non-0, the allocation will be forced to
166 * reside between these offsets in its respective memory heap. The
167 * base address that the offset relates to, depends on the memory
168 * type.
169 *
170 * - CGS_GPU_MEM_TYPE__*_CONTIG_FB: FB MC base address
171 * - CGS_GPU_MEM_TYPE__GART_*: GART aperture base address
172 * - others: undefined, don't use with max_offset
173 *
174 * Return: 0 on success, -errno otherwise
175 */
176typedef int (*cgs_alloc_gpu_mem_t)(void *cgs_device, enum cgs_gpu_mem_type type,
177 uint64_t size, uint64_t align,
178 uint64_t min_offset, uint64_t max_offset,
179 cgs_handle_t *handle);
180
181/**
182 * cgs_free_gpu_mem() - Free GPU memory
183 * @cgs_device: opaque device handle
184 * @handle: memory handle returned by alloc or import
185 *
186 * Return: 0 on success, -errno otherwise
187 */
188typedef int (*cgs_free_gpu_mem_t)(void *cgs_device, cgs_handle_t handle);
189
190/**
191 * cgs_gmap_gpu_mem() - GPU-map GPU memory
192 * @cgs_device: opaque device handle
193 * @handle: memory handle returned by alloc or import
194 * @mcaddr: MC address (output)
195 *
196 * Ensures that a buffer is GPU accessible and returns its MC address.
197 *
198 * Return: 0 on success, -errno otherwise
199 */
200typedef int (*cgs_gmap_gpu_mem_t)(void *cgs_device, cgs_handle_t handle,
201 uint64_t *mcaddr);
202
203/**
204 * cgs_gunmap_gpu_mem() - GPU-unmap GPU memory
205 * @cgs_device: opaque device handle
206 * @handle: memory handle returned by alloc or import
207 *
208 * Allows the buffer to be migrated while it's not used by the GPU.
209 *
210 * Return: 0 on success, -errno otherwise
211 */
212typedef int (*cgs_gunmap_gpu_mem_t)(void *cgs_device, cgs_handle_t handle);
213
214/**
215 * cgs_kmap_gpu_mem() - Kernel-map GPU memory
216 *
217 * @cgs_device: opaque device handle
218 * @handle: memory handle returned by alloc or import
219 * @map: Kernel virtual address the memory was mapped to (output)
220 *
221 * Return: 0 on success, -errno otherwise
222 */
223typedef int (*cgs_kmap_gpu_mem_t)(void *cgs_device, cgs_handle_t handle,
224 void **map);
225
226/**
227 * cgs_kunmap_gpu_mem() - Kernel-unmap GPU memory
228 * @cgs_device: opaque device handle
229 * @handle: memory handle returned by alloc or import
230 *
231 * Return: 0 on success, -errno otherwise
232 */
233typedef int (*cgs_kunmap_gpu_mem_t)(void *cgs_device, cgs_handle_t handle);
234
235/**
236 * cgs_read_register() - Read an MMIO register
237 * @cgs_device: opaque device handle
238 * @offset: register offset
239 *
240 * Return: register value
241 */
242typedef uint32_t (*cgs_read_register_t)(void *cgs_device, unsigned offset);
243
244/**
245 * cgs_write_register() - Write an MMIO register
246 * @cgs_device: opaque device handle
247 * @offset: register offset
248 * @value: register value
249 */
250typedef void (*cgs_write_register_t)(void *cgs_device, unsigned offset,
251 uint32_t value);
252
253/**
254 * cgs_read_ind_register() - Read an indirect register
255 * @cgs_device: opaque device handle
256 * @offset: register offset
257 *
258 * Return: register value
259 */
260typedef uint32_t (*cgs_read_ind_register_t)(void *cgs_device, enum cgs_ind_reg space,
261 unsigned index);
262
263/**
264 * cgs_write_ind_register() - Write an indirect register
265 * @cgs_device: opaque device handle
266 * @offset: register offset
267 * @value: register value
268 */
269typedef void (*cgs_write_ind_register_t)(void *cgs_device, enum cgs_ind_reg space,
270 unsigned index, uint32_t value);
271
272/**
273 * cgs_read_pci_config_byte() - Read byte from PCI configuration space
274 * @cgs_device: opaque device handle
275 * @addr: address
276 *
277 * Return: Value read
278 */
279typedef uint8_t (*cgs_read_pci_config_byte_t)(void *cgs_device, unsigned addr);
280
281/**
282 * cgs_read_pci_config_word() - Read word from PCI configuration space
283 * @cgs_device: opaque device handle
284 * @addr: address, must be word-aligned
285 *
286 * Return: Value read
287 */
288typedef uint16_t (*cgs_read_pci_config_word_t)(void *cgs_device, unsigned addr);
289
290/**
291 * cgs_read_pci_config_dword() - Read dword from PCI configuration space
292 * @cgs_device: opaque device handle
293 * @addr: address, must be dword-aligned
294 *
295 * Return: Value read
296 */
297typedef uint32_t (*cgs_read_pci_config_dword_t)(void *cgs_device,
298 unsigned addr);
299
300/**
301 * cgs_write_pci_config_byte() - Write byte to PCI configuration space
302 * @cgs_device: opaque device handle
303 * @addr: address
304 * @value: value to write
305 */
306typedef void (*cgs_write_pci_config_byte_t)(void *cgs_device, unsigned addr,
307 uint8_t value);
308
309/**
310 * cgs_write_pci_config_word() - Write byte to PCI configuration space
311 * @cgs_device: opaque device handle
312 * @addr: address, must be word-aligned
313 * @value: value to write
314 */
315typedef void (*cgs_write_pci_config_word_t)(void *cgs_device, unsigned addr,
316 uint16_t value);
317
318/**
319 * cgs_write_pci_config_dword() - Write byte to PCI configuration space
320 * @cgs_device: opaque device handle
321 * @addr: address, must be dword-aligned
322 * @value: value to write
323 */
324typedef void (*cgs_write_pci_config_dword_t)(void *cgs_device, unsigned addr,
325 uint32_t value);
326
327/**
328 * cgs_atom_get_data_table() - Get a pointer to an ATOM BIOS data table
329 * @cgs_device: opaque device handle
330 * @table: data table index
331 * @size: size of the table (output, may be NULL)
332 * @frev: table format revision (output, may be NULL)
333 * @crev: table content revision (output, may be NULL)
334 *
335 * Return: Pointer to start of the table, or NULL on failure
336 */
337typedef const void *(*cgs_atom_get_data_table_t)(
338 void *cgs_device, unsigned table,
339 uint16_t *size, uint8_t *frev, uint8_t *crev);
340
341/**
342 * cgs_atom_get_cmd_table_revs() - Get ATOM BIOS command table revisions
343 * @cgs_device: opaque device handle
344 * @table: data table index
345 * @frev: table format revision (output, may be NULL)
346 * @crev: table content revision (output, may be NULL)
347 *
348 * Return: 0 on success, -errno otherwise
349 */
350typedef int (*cgs_atom_get_cmd_table_revs_t)(void *cgs_device, unsigned table,
351 uint8_t *frev, uint8_t *crev);
352
353/**
354 * cgs_atom_exec_cmd_table() - Execute an ATOM BIOS command table
355 * @cgs_device: opaque device handle
356 * @table: command table index
357 * @args: arguments
358 *
359 * Return: 0 on success, -errno otherwise
360 */
361typedef int (*cgs_atom_exec_cmd_table_t)(void *cgs_device,
362 unsigned table, void *args);
363
364/**
365 * cgs_create_pm_request() - Create a power management request
366 * @cgs_device: opaque device handle
367 * @request: handle of created PM request (output)
368 *
369 * Return: 0 on success, -errno otherwise
370 */
371typedef int (*cgs_create_pm_request_t)(void *cgs_device, cgs_handle_t *request);
372
373/**
374 * cgs_destroy_pm_request() - Destroy a power management request
375 * @cgs_device: opaque device handle
376 * @request: handle of created PM request
377 *
378 * Return: 0 on success, -errno otherwise
379 */
380typedef int (*cgs_destroy_pm_request_t)(void *cgs_device, cgs_handle_t request);
381
382/**
383 * cgs_set_pm_request() - Activate or deactiveate a PM request
384 * @cgs_device: opaque device handle
385 * @request: PM request handle
386 * @active: 0 = deactivate, non-0 = activate
387 *
388 * While a PM request is active, its minimum clock requests are taken
389 * into account as the requested engines are powered up. When the
390 * request is inactive, the engines may be powered down and clocks may
391 * be lower, depending on other PM requests by other driver
392 * components.
393 *
394 * Return: 0 on success, -errno otherwise
395 */
396typedef int (*cgs_set_pm_request_t)(void *cgs_device, cgs_handle_t request,
397 int active);
398
399/**
400 * cgs_pm_request_clock() - Request a minimum frequency for a specific clock
401 * @cgs_device: opaque device handle
402 * @request: PM request handle
403 * @clock: which clock?
404 * @freq: requested min. frequency in 10KHz units (0 to clear request)
405 *
406 * Return: 0 on success, -errno otherwise
407 */
408typedef int (*cgs_pm_request_clock_t)(void *cgs_device, cgs_handle_t request,
409 enum cgs_clock clock, unsigned freq);
410
411/**
412 * cgs_pm_request_engine() - Request an engine to be powered up
413 * @cgs_device: opaque device handle
414 * @request: PM request handle
415 * @engine: which engine?
416 * @powered: 0 = powered down, non-0 = powered up
417 *
418 * Return: 0 on success, -errno otherwise
419 */
420typedef int (*cgs_pm_request_engine_t)(void *cgs_device, cgs_handle_t request,
421 enum cgs_engine engine, int powered);
422
423/**
424 * cgs_pm_query_clock_limits() - Query clock frequency limits
425 * @cgs_device: opaque device handle
426 * @clock: which clock?
427 * @limits: clock limits
428 *
429 * Return: 0 on success, -errno otherwise
430 */
431typedef int (*cgs_pm_query_clock_limits_t)(void *cgs_device,
432 enum cgs_clock clock,
433 struct cgs_clock_limits *limits);
434
435/**
436 * cgs_set_camera_voltages() - Apply specific voltages to PMIC voltage planes
437 * @cgs_device: opaque device handle
438 * @mask: bitmask of voltages to change (1<<CGS_VOLTAGE_PLANE__xyz|...)
439 * @voltages: pointer to array of voltage values in 1mV units
440 *
441 * Return: 0 on success, -errno otherwise
442 */
443typedef int (*cgs_set_camera_voltages_t)(void *cgs_device, uint32_t mask,
444 const uint32_t *voltages);
445
446struct cgs_ops {
447 /* memory management calls (similar to KFD interface) */
448 cgs_gpu_mem_info_t gpu_mem_info;
449 cgs_gmap_kmem_t gmap_kmem;
450 cgs_gunmap_kmem_t gunmap_kmem;
451 cgs_alloc_gpu_mem_t alloc_gpu_mem;
452 cgs_free_gpu_mem_t free_gpu_mem;
453 cgs_gmap_gpu_mem_t gmap_gpu_mem;
454 cgs_gunmap_gpu_mem_t gunmap_gpu_mem;
455 cgs_kmap_gpu_mem_t kmap_gpu_mem;
456 cgs_kunmap_gpu_mem_t kunmap_gpu_mem;
457 /* MMIO access */
458 cgs_read_register_t read_register;
459 cgs_write_register_t write_register;
460 cgs_read_ind_register_t read_ind_register;
461 cgs_write_ind_register_t write_ind_register;
462 /* PCI configuration space access */
463 cgs_read_pci_config_byte_t read_pci_config_byte;
464 cgs_read_pci_config_word_t read_pci_config_word;
465 cgs_read_pci_config_dword_t read_pci_config_dword;
466 cgs_write_pci_config_byte_t write_pci_config_byte;
467 cgs_write_pci_config_word_t write_pci_config_word;
468 cgs_write_pci_config_dword_t write_pci_config_dword;
469 /* ATOM BIOS */
470 cgs_atom_get_data_table_t atom_get_data_table;
471 cgs_atom_get_cmd_table_revs_t atom_get_cmd_table_revs;
472 cgs_atom_exec_cmd_table_t atom_exec_cmd_table;
473 /* Power management */
474 cgs_create_pm_request_t create_pm_request;
475 cgs_destroy_pm_request_t destroy_pm_request;
476 cgs_set_pm_request_t set_pm_request;
477 cgs_pm_request_clock_t pm_request_clock;
478 cgs_pm_request_engine_t pm_request_engine;
479 cgs_pm_query_clock_limits_t pm_query_clock_limits;
480 cgs_set_camera_voltages_t set_camera_voltages;
481 /* ACPI (TODO) */
482};
483
484struct cgs_os_ops; /* To be define in OS-specific CGS header */
485
486struct cgs_device
487{
488 const struct cgs_ops *ops;
489 const struct cgs_os_ops *os_ops;
490 /* to be embedded at the start of driver private structure */
491};
492
493/* Convenience macros that make CGS indirect function calls look like
494 * normal function calls */
495#define CGS_CALL(func,dev,...) \
496 (((struct cgs_device *)dev)->ops->func(dev, ##__VA_ARGS__))
497#define CGS_OS_CALL(func,dev,...) \
498 (((struct cgs_device *)dev)->os_ops->func(dev, ##__VA_ARGS__))
499
500#define cgs_gpu_mem_info(dev,type,mc_start,mc_size,mem_size) \
501 CGS_CALL(gpu_mem_info,dev,type,mc_start,mc_size,mem_size)
502#define cgs_gmap_kmem(dev,kmem,size,min_off,max_off,kmem_handle,mcaddr) \
503 CGS_CALL(gmap_kmem,dev,kmem,size,min_off,max_off,kmem_handle,mcaddr)
504#define cgs_gummap_kmem(dev,kmem_handle) \
505 CGS_CALL(gunmap_kmem,dev,keme_handle)
506#define cgs_alloc_gpu_mem(dev,type,size,align,min_off,max_off,handle) \
507 CGS_CALL(alloc_gpu_mem,dev,type,size,align,min_off,max_off,handle)
508#define cgs_free_gpu_mem(dev,handle) \
509 CGS_CALL(free_gpu_mem,dev,handle)
510#define cgs_gmap_gpu_mem(dev,handle,mcaddr) \
511 CGS_CALL(gmap_gpu_mem,dev,handle,mcaddr)
512#define cgs_gummap_gpu_mem(dev,handle) \
513 CGS_CALL(gunmap_gpu_mem,dev,handle)
514#define cgs_kmap_gpu_mem(dev,handle,map) \
515 CGS_CALL(kmap_gpu_mem,dev,handle,map)
516#define cgs_kunmap_gpu_mem(dev,handle) \
517 CGS_CALL(kunmap_gpu_mem,dev,handle)
518
519#define cgs_read_register(dev,offset) \
520 CGS_CALL(read_register,dev,offset)
521#define cgs_write_register(dev,offset,value) \
522 CGS_CALL(write_register,dev,offset,value)
523#define cgs_read_ind_register(dev,space,index) \
524 CGS_CALL(read_ind_register,dev,space,index)
525#define cgs_write_ind_register(dev,space,index,value) \
526 CGS_CALL(write_ind_register,dev,space,index,value)
527
528#define cgs_read_pci_config_byte(dev,addr) \
529 CGS_CALL(read_pci_config_byte,dev,addr)
530#define cgs_read_pci_config_word(dev,addr) \
531 CGS_CALL(read_pci_config_word,dev,addr)
532#define cgs_read_pci_config_dword(dev,addr) \
533 CGS_CALL(read_pci_config_dword,dev,addr)
534#define cgs_write_pci_config_byte(dev,addr,value) \
535 CGS_CALL(write_pci_config_byte,dev,addr,value)
536#define cgs_write_pci_config_word(dev,addr,value) \
537 CGS_CALL(write_pci_config_word,dev,addr,value)
538#define cgs_write_pci_config_dword(dev,addr,value) \
539 CGS_CALL(write_pci_config_dword,dev,addr,value)
540
541#define cgs_atom_get_data_table(dev,table,size,frev,crev) \
542 CGS_CALL(atom_get_data_table,dev,table,size,frev,crev)
543#define cgs_atom_get_cmd_table_revs(dev,table,frev,crev) \
544 CGS_CALL(atom_get_cmd_table_revs,dev,table,frev,crev)
545#define cgs_atom_exec_cmd_table(dev,table,args) \
546 CGS_CALL(atom_exec_cmd_table,dev,table,args)
547
548#define cgs_create_pm_request(dev,request) \
549 CGS_CALL(create_pm_request,dev,request)
550#define cgs_destroy_pm_request(dev,request) \
551 CGS_CALL(destroy_pm_request,dev,request)
552#define cgs_set_pm_request(dev,request,active) \
553 CGS_CALL(set_pm_request,dev,request,active)
554#define cgs_pm_request_clock(dev,request,clock,freq) \
555 CGS_CALL(pm_request_clock,dev,request,clock,freq)
556#define cgs_pm_request_engine(dev,request,engine,powered) \
557 CGS_CALL(pm_request_engine,dev,request,engine,powered)
558#define cgs_pm_query_clock_limits(dev,clock,limits) \
559 CGS_CALL(pm_query_clock_limits,dev,clock,limits)
560#define cgs_set_camera_voltages(dev,mask,voltages) \
561 CGS_CALL(set_camera_voltages,dev,mask,voltages)
562
563#endif /* _CGS_COMMON_H */