1 /* 2 * Copyright (C) 2013 Red Hat 3 * Author: Rob Clark <robdclark@gmail.com> 4 * 5 * Copyright (c) 2014 The Linux Foundation. All rights reserved. 6 * 7 * This program is free software; you can redistribute it and/or modify it 8 * under the terms of the GNU General Public License version 2 as published by 9 * the Free Software Foundation. 10 * 11 * This program is distributed in the hope that it will be useful, but WITHOUT 12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for 14 * more details. 15 * 16 * You should have received a copy of the GNU General Public License along with 17 * this program. If not, see <http://www.gnu.org/licenses/>. 18 */ 19 20 #ifndef __ADRENO_GPU_H__ 21 #define __ADRENO_GPU_H__ 22 23 #include <linux/firmware.h> 24 25 #include "msm_gpu.h" 26 27 #include "adreno_common.xml.h" 28 #include "adreno_pm4.xml.h" 29 30 #define REG_ADRENO_DEFINE(_offset, _reg) [_offset] = (_reg) + 1 31 /** 32 * adreno_regs: List of registers that are used in across all 33 * 3D devices. Each device type has different offset value for the same 34 * register, so an array of register offsets are declared for every device 35 * and are indexed by the enumeration values defined in this enum 36 */ 37 enum adreno_regs { 38 REG_ADRENO_CP_DEBUG, 39 REG_ADRENO_CP_ME_RAM_WADDR, 40 REG_ADRENO_CP_ME_RAM_DATA, 41 REG_ADRENO_CP_PFP_UCODE_DATA, 42 REG_ADRENO_CP_PFP_UCODE_ADDR, 43 REG_ADRENO_CP_WFI_PEND_CTR, 44 REG_ADRENO_CP_RB_BASE, 45 REG_ADRENO_CP_RB_RPTR_ADDR, 46 REG_ADRENO_CP_RB_RPTR, 47 REG_ADRENO_CP_RB_WPTR, 48 REG_ADRENO_CP_PROTECT_CTRL, 49 REG_ADRENO_CP_ME_CNTL, 50 REG_ADRENO_CP_RB_CNTL, 51 REG_ADRENO_CP_IB1_BASE, 52 REG_ADRENO_CP_IB1_BUFSZ, 53 REG_ADRENO_CP_IB2_BASE, 54 REG_ADRENO_CP_IB2_BUFSZ, 55 REG_ADRENO_CP_TIMESTAMP, 56 REG_ADRENO_CP_ME_RAM_RADDR, 57 REG_ADRENO_CP_ROQ_ADDR, 58 REG_ADRENO_CP_ROQ_DATA, 59 REG_ADRENO_CP_MERCIU_ADDR, 60 REG_ADRENO_CP_MERCIU_DATA, 61 REG_ADRENO_CP_MERCIU_DATA2, 62 REG_ADRENO_CP_MEQ_ADDR, 63 REG_ADRENO_CP_MEQ_DATA, 64 REG_ADRENO_CP_HW_FAULT, 65 REG_ADRENO_CP_PROTECT_STATUS, 66 REG_ADRENO_SCRATCH_ADDR, 67 REG_ADRENO_SCRATCH_UMSK, 68 REG_ADRENO_SCRATCH_REG2, 69 REG_ADRENO_RBBM_STATUS, 70 REG_ADRENO_RBBM_PERFCTR_CTL, 71 REG_ADRENO_RBBM_PERFCTR_LOAD_CMD0, 72 REG_ADRENO_RBBM_PERFCTR_LOAD_CMD1, 73 REG_ADRENO_RBBM_PERFCTR_LOAD_CMD2, 74 REG_ADRENO_RBBM_PERFCTR_PWR_1_LO, 75 REG_ADRENO_RBBM_INT_0_MASK, 76 REG_ADRENO_RBBM_INT_0_STATUS, 77 REG_ADRENO_RBBM_AHB_ERROR_STATUS, 78 REG_ADRENO_RBBM_PM_OVERRIDE2, 79 REG_ADRENO_RBBM_AHB_CMD, 80 REG_ADRENO_RBBM_INT_CLEAR_CMD, 81 REG_ADRENO_RBBM_SW_RESET_CMD, 82 REG_ADRENO_RBBM_CLOCK_CTL, 83 REG_ADRENO_RBBM_AHB_ME_SPLIT_STATUS, 84 REG_ADRENO_RBBM_AHB_PFP_SPLIT_STATUS, 85 REG_ADRENO_VPC_DEBUG_RAM_SEL, 86 REG_ADRENO_VPC_DEBUG_RAM_READ, 87 REG_ADRENO_VSC_SIZE_ADDRESS, 88 REG_ADRENO_VFD_CONTROL_0, 89 REG_ADRENO_VFD_INDEX_MAX, 90 REG_ADRENO_SP_VS_PVT_MEM_ADDR_REG, 91 REG_ADRENO_SP_FS_PVT_MEM_ADDR_REG, 92 REG_ADRENO_SP_VS_OBJ_START_REG, 93 REG_ADRENO_SP_FS_OBJ_START_REG, 94 REG_ADRENO_PA_SC_AA_CONFIG, 95 REG_ADRENO_SQ_GPR_MANAGEMENT, 96 REG_ADRENO_SQ_INST_STORE_MANAGMENT, 97 REG_ADRENO_TP0_CHICKEN, 98 REG_ADRENO_RBBM_RBBM_CTL, 99 REG_ADRENO_UCHE_INVALIDATE0, 100 REG_ADRENO_RBBM_PERFCTR_LOAD_VALUE_LO, 101 REG_ADRENO_RBBM_PERFCTR_LOAD_VALUE_HI, 102 REG_ADRENO_REGISTER_MAX, 103 }; 104 105 struct adreno_rev { 106 uint8_t core; 107 uint8_t major; 108 uint8_t minor; 109 uint8_t patchid; 110 }; 111 112 #define ADRENO_REV(core, major, minor, patchid) \ 113 ((struct adreno_rev){ core, major, minor, patchid }) 114 115 struct adreno_gpu_funcs { 116 struct msm_gpu_funcs base; 117 }; 118 119 struct adreno_info { 120 struct adreno_rev rev; 121 uint32_t revn; 122 const char *name; 123 const char *pm4fw, *pfpfw; 124 uint32_t gmem; 125 struct msm_gpu *(*init)(struct drm_device *dev); 126 }; 127 128 const struct adreno_info *adreno_info(struct adreno_rev rev); 129 130 struct adreno_rbmemptrs { 131 volatile uint32_t rptr; 132 volatile uint32_t wptr; 133 volatile uint32_t fence; 134 }; 135 136 struct adreno_gpu { 137 struct msm_gpu base; 138 struct adreno_rev rev; 139 const struct adreno_info *info; 140 uint32_t gmem; /* actual gmem size */ 141 uint32_t revn; /* numeric revision name */ 142 const struct adreno_gpu_funcs *funcs; 143 144 /* interesting register offsets to dump: */ 145 const unsigned int *registers; 146 147 /* firmware: */ 148 const struct firmware *pm4, *pfp; 149 150 /* ringbuffer rptr/wptr: */ 151 // TODO should this be in msm_ringbuffer? I think it would be 152 // different for z180.. 153 struct adreno_rbmemptrs *memptrs; 154 struct drm_gem_object *memptrs_bo; 155 uint32_t memptrs_iova; 156 157 /* 158 * Register offsets are different between some GPUs. 159 * GPU specific offsets will be exported by GPU specific 160 * code (a3xx_gpu.c) and stored in this common location. 161 */ 162 const unsigned int *reg_offsets; 163 }; 164 #define to_adreno_gpu(x) container_of(x, struct adreno_gpu, base) 165 166 /* platform config data (ie. from DT, or pdata) */ 167 struct adreno_platform_config { 168 struct adreno_rev rev; 169 uint32_t fast_rate, slow_rate, bus_freq; 170 #ifdef CONFIG_MSM_BUS_SCALING 171 struct msm_bus_scale_pdata *bus_scale_table; 172 #endif 173 }; 174 175 #define ADRENO_IDLE_TIMEOUT msecs_to_jiffies(1000) 176 177 #define spin_until(X) ({ \ 178 int __ret = -ETIMEDOUT; \ 179 unsigned long __t = jiffies + ADRENO_IDLE_TIMEOUT; \ 180 do { \ 181 if (X) { \ 182 __ret = 0; \ 183 break; \ 184 } \ 185 } while (time_before(jiffies, __t)); \ 186 __ret; \ 187 }) 188 189 190 static inline bool adreno_is_a3xx(struct adreno_gpu *gpu) 191 { 192 return (gpu->revn >= 300) && (gpu->revn < 400); 193 } 194 195 static inline bool adreno_is_a305(struct adreno_gpu *gpu) 196 { 197 return gpu->revn == 305; 198 } 199 200 static inline bool adreno_is_a320(struct adreno_gpu *gpu) 201 { 202 return gpu->revn == 320; 203 } 204 205 static inline bool adreno_is_a330(struct adreno_gpu *gpu) 206 { 207 return gpu->revn == 330; 208 } 209 210 static inline bool adreno_is_a330v2(struct adreno_gpu *gpu) 211 { 212 return adreno_is_a330(gpu) && (gpu->rev.patchid > 0); 213 } 214 215 static inline bool adreno_is_a4xx(struct adreno_gpu *gpu) 216 { 217 return (gpu->revn >= 400) && (gpu->revn < 500); 218 } 219 220 static inline int adreno_is_a420(struct adreno_gpu *gpu) 221 { 222 return gpu->revn == 420; 223 } 224 225 int adreno_get_param(struct msm_gpu *gpu, uint32_t param, uint64_t *value); 226 int adreno_hw_init(struct msm_gpu *gpu); 227 uint32_t adreno_last_fence(struct msm_gpu *gpu); 228 void adreno_recover(struct msm_gpu *gpu); 229 int adreno_submit(struct msm_gpu *gpu, struct msm_gem_submit *submit, 230 struct msm_file_private *ctx); 231 void adreno_flush(struct msm_gpu *gpu); 232 void adreno_idle(struct msm_gpu *gpu); 233 #ifdef CONFIG_DEBUG_FS 234 void adreno_show(struct msm_gpu *gpu, struct seq_file *m); 235 #endif 236 void adreno_dump(struct msm_gpu *gpu); 237 void adreno_wait_ring(struct msm_gpu *gpu, uint32_t ndwords); 238 239 int adreno_gpu_init(struct drm_device *drm, struct platform_device *pdev, 240 struct adreno_gpu *gpu, const struct adreno_gpu_funcs *funcs); 241 void adreno_gpu_cleanup(struct adreno_gpu *gpu); 242 243 244 /* ringbuffer helpers (the parts that are adreno specific) */ 245 246 static inline void 247 OUT_PKT0(struct msm_ringbuffer *ring, uint16_t regindx, uint16_t cnt) 248 { 249 adreno_wait_ring(ring->gpu, cnt+1); 250 OUT_RING(ring, CP_TYPE0_PKT | ((cnt-1) << 16) | (regindx & 0x7FFF)); 251 } 252 253 /* no-op packet: */ 254 static inline void 255 OUT_PKT2(struct msm_ringbuffer *ring) 256 { 257 adreno_wait_ring(ring->gpu, 1); 258 OUT_RING(ring, CP_TYPE2_PKT); 259 } 260 261 static inline void 262 OUT_PKT3(struct msm_ringbuffer *ring, uint8_t opcode, uint16_t cnt) 263 { 264 adreno_wait_ring(ring->gpu, cnt+1); 265 OUT_RING(ring, CP_TYPE3_PKT | ((cnt-1) << 16) | ((opcode & 0xFF) << 8)); 266 } 267 268 /* 269 * adreno_checkreg_off() - Checks the validity of a register enum 270 * @gpu: Pointer to struct adreno_gpu 271 * @offset_name: The register enum that is checked 272 */ 273 static inline bool adreno_reg_check(struct adreno_gpu *gpu, 274 enum adreno_regs offset_name) 275 { 276 if (offset_name >= REG_ADRENO_REGISTER_MAX || 277 !gpu->reg_offsets[offset_name]) { 278 BUG(); 279 } 280 return true; 281 } 282 283 static inline u32 adreno_gpu_read(struct adreno_gpu *gpu, 284 enum adreno_regs offset_name) 285 { 286 u32 reg = gpu->reg_offsets[offset_name]; 287 u32 val = 0; 288 if(adreno_reg_check(gpu,offset_name)) 289 val = gpu_read(&gpu->base, reg - 1); 290 return val; 291 } 292 293 static inline void adreno_gpu_write(struct adreno_gpu *gpu, 294 enum adreno_regs offset_name, u32 data) 295 { 296 u32 reg = gpu->reg_offsets[offset_name]; 297 if(adreno_reg_check(gpu, offset_name)) 298 gpu_write(&gpu->base, reg - 1, data); 299 } 300 301 #endif /* __ADRENO_GPU_H__ */ 302