/* * Copyright © 2014 Intel Corporation * * Permission is hereby granted, free of charge, to any person obtaining a * copy of this software and associated documentation files (the "Software"), * to deal in the Software without restriction, including without limitation * the rights to use, copy, modify, merge, publish, distribute, sublicense, * and/or sell copies of the Software, and to permit persons to whom the * Software is furnished to do so, subject to the following conditions: * * The above copyright notice and this permission notice (including the next * paragraph) shall be included in all copies or substantial portions of the * Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER * DEALINGS IN THE SOFTWARE. */ #include #include #include #include #include #include #include "main.h" #include "i915_reg.h" int process_dumpgtt(char *cmdhdr,unsigned int fbaddr,unsigned int size) { uint32_t i,start_entry,end_entry,total_entries; uint32_t aligned_size, entries = 0; uint64_t *p, previous_entry=0; //const char *type = "1:valid,2:WR,4:RO,8:cached"; if (fbaddr >= gtt_mapable_size) { printf("Address 0x%x is out of GTT mappable range 0x%x\n", fbaddr, gtt_mapable_size/4096); return 0; } total_entries = gtt_mapable_size/4096; start_entry = fbaddr/4096; aligned_size = (size + 4095) & (~4095); entries = aligned_size / 4096; end_entry = min(start_entry + entries, total_entries); fprintf(stdout,"\nGTT entry from entry %d to %d(total %d, size %d/%dK)\n", start_entry,end_entry,end_entry - start_entry + 1, size, size/1024); fprintf(stdout,"\nSkip if the entry map to same address\n"); p =(uint64_t *)((char *)linear_gtt + 8*start_entry); for (i=start_entry;i>8,(i<<2)&0x3ff,(unsigned char *)p-linear_gtt-8, i); fprintf(stdout," %010x", (uint32_t)tmp); if (verbose) fprintf(stdout," page no.=%06d(%04dM+%04dK),map type=0x%x", (tmp1>>12),(tmp1>>20),(tmp1>>10)&0x3ff,tmp1&0xf); fprintf(stdout,"\n"); } return 0; } int process_stolen(char *cmdhdr) { uint32_t stolen_phy_start = stolen_base; uint32_t stolen_phy_end = stolen_base + stolen_size; uint32_t i, start_i=~0, total_entry = gtt_size / 8; uint64_t *p, previous_entry=0; printf("Dump all stolen memory mappings in GTT\n"); p =(uint64_t *)linear_gtt; for (i=0;istolen_phy_end) continue; if (i != start_i) { printf("\n-----------------------------%03dM+%04dK FB------------------------------\n", i>>8,(i<<2)&0x3ff); start_i = i; } start_i++; fprintf(stdout,"FB:0x%07x|%03dM+%04dK|GTT offset:0x%05lx(entry 0x%05x):", i*4096,i>>8,(i<<2)&0x3ff,(unsigned char *)p-linear_gtt-8,i); fprintf(stdout," %010x", (uint32_t)tmp); if (verbose) fprintf(stdout," page no.=%06d(%04dM+%04dK),map type=0x%x", (tmp1>>12),(tmp1>>20),(tmp1>>10)&0x3ff,tmp1&0xf); fprintf(stdout,"\n"); } return 0; } static uint32_t old_lsb; static uint32_t old_msb; static int set_fence(unsigned int offset, unsigned int size) { unsigned int force_stride = 5120; unsigned int fence_idx = 0; uint32_t fencereg_offset = 0x100000; uint32_t lsb = (offset & 0xfffff000) | 1; uint32_t msb = ((offset + size + 0xfff) & 0xfffff000) | (force_stride/128 -1); old_lsb = INREG(linear_mmio, fence_idx*8 + fencereg_offset); old_msb = INREG(linear_mmio, (fence_idx*8 + 4) + fencereg_offset); printf("Force FENCE0 for linear access with stride %d\n", force_stride); OUTREG(linear_mmio, fence_idx*8 + fencereg_offset, lsb); OUTREG(linear_mmio, (fence_idx*8 + 4) + fencereg_offset, msb); return 0; } static int unset_fence() { uint32_t fencereg_offset = 0x100000; int fence_idx = 0; printf("Restore FENCE0\n"); OUTREG(linear_mmio, fence_idx*8 + fencereg_offset, old_lsb); OUTREG(linear_mmio, (fence_idx*8 + 4) + fencereg_offset, old_msb); return 0; } int process_fillfb(char *cmdhdr,unsigned int offset, unsigned int size,unsigned int value) { printf("Fill frame buffer from offset 0x%x (%dM+%dK),with value 0x%x,size %d\n", offset,offset>>20, (offset>>10)&0x3ff,value,size); if ((offset>>20) > FB_MMAP_MB) { printf("!!!!!Sorry, Out of aperture mmap range %dM!!!!!\n", FB_MMAP_MB); return 0; } memset((char *)(linear_fb+offset),value,size); return 0; } int process_fillfbl(char *cmdhdr,unsigned int offset, unsigned int size,unsigned int value) { set_fence(offset, size); process_fillfb(NULL, offset, size, value); unset_fence(); return 0; } int process_dumpfb(char *cmdhdr,unsigned int offset, unsigned int size) { unsigned int i; printf("Dump frame buffer from offset 0x%x,size %d\n",offset,size); for (i=0;i>1)&1?'Y':'X', addr, addr>>20, (addr>>10)&0x3ff); addr = msb&(~0xfff); fprintf(stdout,"FENCDE%d_MSB:0x%08x (pitch=%d,size=%dK,end addr:0x%08x(%dM+%dK))\n", i, msb, ((msb&0x7ff) + 1) * 128, ((msb&(~0xfff)) - (lsb&(~0xfff))) >> 10 , addr, addr>>20, (addr>>10)&0x3ff); printf("\n"); } return 0; }