/drivers/video/drm/radeon/dce6_afmt.c |
---|
301,6 → 301,14 |
* is the numerator, DCCG_AUDIO_DTOx_MODULE is the denominator |
*/ |
if (ASIC_IS_DCE8(rdev)) { |
unsigned int div = (RREG32(DENTIST_DISPCLK_CNTL) & |
DENTIST_DPREFCLK_WDIVIDER_MASK) >> |
DENTIST_DPREFCLK_WDIVIDER_SHIFT; |
div = radeon_audio_decode_dfs_div(div); |
if (div) |
clock = clock * 100 / div; |
WREG32(DCE8_DCCG_AUDIO_DTO1_PHASE, 24000); |
WREG32(DCE8_DCCG_AUDIO_DTO1_MODULE, clock); |
} else { |
/drivers/video/drm/radeon/evergreen_hdmi.c |
---|
289,6 → 289,16 |
* number (coefficient of two integer numbers. DCCG_AUDIO_DTOx_PHASE |
* is the numerator, DCCG_AUDIO_DTOx_MODULE is the denominator |
*/ |
if (ASIC_IS_DCE41(rdev)) { |
unsigned int div = (RREG32(DCE41_DENTIST_DISPCLK_CNTL) & |
DENTIST_DPREFCLK_WDIVIDER_MASK) >> |
DENTIST_DPREFCLK_WDIVIDER_SHIFT; |
div = radeon_audio_decode_dfs_div(div); |
if (div) |
clock = 100 * clock / div; |
} |
WREG32(DCCG_AUDIO_DTO1_PHASE, 24000); |
WREG32(DCCG_AUDIO_DTO1_MODULE, clock); |
} |
/drivers/video/drm/radeon/evergreend.h |
---|
511,6 → 511,11 |
#define DCCG_AUDIO_DTO1_CNTL 0x05cc |
# define DCCG_AUDIO_DTO1_USE_512FBR_DTO (1 << 3) |
#define DCE41_DENTIST_DISPCLK_CNTL 0x049c |
# define DENTIST_DPREFCLK_WDIVIDER(x) (((x) & 0x7f) << 24) |
# define DENTIST_DPREFCLK_WDIVIDER_MASK (0x7f << 24) |
# define DENTIST_DPREFCLK_WDIVIDER_SHIFT 24 |
/* DCE 4.0 AFMT */ |
#define HDMI_CONTROL 0x7030 |
# define HDMI_KEEPOUT_MODE (1 << 0) |
/drivers/video/drm/radeon/main.c |
---|
5,7 → 5,7 |
#include "radeon.h" |
#include "bitmap.h" |
#define DRV_NAME "atikms v4.4" |
#define DRV_NAME "atikms v4.4.5-dbg1" |
void __init dmi_scan_machine(void); |
/drivers/video/drm/radeon/pci.c |
---|
1,5 → 1,3 |
#define CONFIG_PCI |
#include <syscall.h> |
#include <linux/kernel.h> |
10,7 → 8,6 |
#include <linux/pci.h> |
extern int pci_scan_filter(u32 id, u32 busnr, u32 devfn); |
static LIST_HEAD(devices); |
669,13 → 666,6 |
} |
static inline void |
_pcibios_resource_to_bus(struct pci_dev *dev, struct pci_bus_region *region, |
struct resource *res) |
{ |
region->start = res->start; |
region->end = res->end; |
} |
int pci_enable_rom(struct pci_dev *pdev) |
/drivers/video/drm/radeon/r600.c |
---|
3128,6 → 3128,11 |
return r; |
} |
r = radeon_audio_init(rdev); |
if (r) { |
DRM_ERROR("radeon: audio init failed\n"); |
return r; |
} |
return 0; |
} |
/drivers/video/drm/radeon/radeon.h |
---|
120,18 → 120,6 |
extern int radeon_auxch; |
extern int radeon_mst; |
static inline u32 ioread32(const volatile void __iomem *addr) |
{ |
return in32((u32)addr); |
} |
//static inline void iowrite32(uint32_t b, volatile void __iomem *addr) |
//{ |
// out32((u32)addr, b); |
//} |
/* |
* Copy from radeon_drv.h so we don't have to include both and have conflicting |
* symbol; |
286,6 → 274,7 |
uint32_t current_dispclk; |
uint32_t dp_extclk; |
uint32_t max_pixel_clock; |
uint32_t vco_freq; |
}; |
/* |
2386,7 → 2375,8 |
struct r600_ih ih; /* r6/700 interrupt ring */ |
struct radeon_rlc rlc; |
struct radeon_mec mec; |
struct work_struct hotplug_work; |
struct delayed_work hotplug_work; |
struct work_struct dp_work; |
struct work_struct audio_work; |
int num_crtc; /* number of crtcs */ |
struct mutex dc_hw_i2c_mutex; /* display controller hw i2c mutex */ |
2937,5 → 2927,6 |
resource_size_t |
drm_get_resource_len(struct drm_device *dev, unsigned int resource); |
#define ioread32(addr) readl(addr) |
#endif |
/drivers/video/drm/radeon/radeon_asic.c |
---|
256,8 → 256,7 |
.set_clock_gating = &radeon_legacy_set_clock_gating, |
}, |
.pflip = { |
// .pre_page_flip = &r100_pre_page_flip, |
// .page_flip = &r100_page_flip, |
}, |
}; |
/drivers/video/drm/radeon/radeon_atombios.c |
---|
437,7 → 437,9 |
} |
/* Fujitsu D3003-S2 board lists DVI-I as DVI-D and VGA */ |
if (((dev->pdev->device == 0x9802) || (dev->pdev->device == 0x9806)) && |
if (((dev->pdev->device == 0x9802) || |
(dev->pdev->device == 0x9805) || |
(dev->pdev->device == 0x9806)) && |
(dev->pdev->subsystem_vendor == 0x1734) && |
(dev->pdev->subsystem_device == 0x11bd)) { |
if (*connector_type == DRM_MODE_CONNECTOR_VGA) { |
448,14 → 450,6 |
} |
} |
/* Fujitsu D3003-S2 board lists DVI-I as DVI-I and VGA */ |
if ((dev->pdev->device == 0x9805) && |
(dev->pdev->subsystem_vendor == 0x1734) && |
(dev->pdev->subsystem_device == 0x11bd)) { |
if (*connector_type == DRM_MODE_CONNECTOR_VGA) |
return false; |
} |
return true; |
} |
1112,6 → 1106,31 |
ATOM_FIRMWARE_INFO_V2_2 info_22; |
}; |
union igp_info { |
struct _ATOM_INTEGRATED_SYSTEM_INFO info; |
struct _ATOM_INTEGRATED_SYSTEM_INFO_V2 info_2; |
struct _ATOM_INTEGRATED_SYSTEM_INFO_V6 info_6; |
struct _ATOM_INTEGRATED_SYSTEM_INFO_V1_7 info_7; |
struct _ATOM_INTEGRATED_SYSTEM_INFO_V1_8 info_8; |
}; |
static void radeon_atombios_get_dentist_vco_freq(struct radeon_device *rdev) |
{ |
struct radeon_mode_info *mode_info = &rdev->mode_info; |
int index = GetIndexIntoMasterTable(DATA, IntegratedSystemInfo); |
union igp_info *igp_info; |
u8 frev, crev; |
u16 data_offset; |
if (atom_parse_data_header(mode_info->atom_context, index, NULL, |
&frev, &crev, &data_offset)) { |
igp_info = (union igp_info *)(mode_info->atom_context->bios + |
data_offset); |
rdev->clock.vco_freq = |
le32_to_cpu(igp_info->info_6.ulDentistVCOFreq); |
} |
} |
bool radeon_atom_get_clock_info(struct drm_device *dev) |
{ |
struct radeon_device *rdev = dev->dev_private; |
1263,6 → 1282,19 |
rdev->mode_info.firmware_flags = |
le16_to_cpu(firmware_info->info.usFirmwareCapability.susAccess); |
if (ASIC_IS_DCE8(rdev)) |
rdev->clock.vco_freq = |
le32_to_cpu(firmware_info->info_22.ulGPUPLL_OutputFreq); |
else if (ASIC_IS_DCE5(rdev)) |
rdev->clock.vco_freq = rdev->clock.current_dispclk; |
else if (ASIC_IS_DCE41(rdev)) |
radeon_atombios_get_dentist_vco_freq(rdev); |
else |
rdev->clock.vco_freq = rdev->clock.current_dispclk; |
if (rdev->clock.vco_freq == 0) |
rdev->clock.vco_freq = 360000; /* 3.6 GHz */ |
return true; |
} |
1269,14 → 1301,6 |
return false; |
} |
union igp_info { |
struct _ATOM_INTEGRATED_SYSTEM_INFO info; |
struct _ATOM_INTEGRATED_SYSTEM_INFO_V2 info_2; |
struct _ATOM_INTEGRATED_SYSTEM_INFO_V6 info_6; |
struct _ATOM_INTEGRATED_SYSTEM_INFO_V1_7 info_7; |
struct _ATOM_INTEGRATED_SYSTEM_INFO_V1_8 info_8; |
}; |
bool radeon_atombios_sideport_present(struct radeon_device *rdev) |
{ |
struct radeon_mode_info *mode_info = &rdev->mode_info; |
/drivers/video/drm/radeon/radeon_audio.c |
---|
22,7 → 22,7 |
* Authors: Slava Grigorev <slava.grigorev@amd.com> |
*/ |
//#include <linux/gcd.h> |
#include <linux/gcd.h> |
#include <drm/drmP.h> |
#include <drm/drm_crtc.h> |
#include "radeon.h" |
739,9 → 739,6 |
struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); |
struct radeon_encoder_atom_dig *dig = radeon_encoder->enc_priv; |
struct drm_connector *connector = radeon_get_connector_for_encoder(encoder); |
struct radeon_connector *radeon_connector = to_radeon_connector(connector); |
struct radeon_connector_atom_dig *dig_connector = |
radeon_connector->con_priv; |
if (!dig || !dig->afmt) |
return; |
753,10 → 750,7 |
radeon_audio_write_speaker_allocation(encoder); |
radeon_audio_write_sad_regs(encoder); |
radeon_audio_write_latency_fields(encoder, mode); |
if (rdev->clock.dp_extclk || ASIC_IS_DCE5(rdev)) |
radeon_audio_set_dto(encoder, rdev->clock.default_dispclk * 10); |
else |
radeon_audio_set_dto(encoder, dig_connector->dp_clock); |
radeon_audio_set_dto(encoder, rdev->clock.vco_freq * 10); |
radeon_audio_set_audio_packet(encoder); |
radeon_audio_select_pin(encoder); |
781,3 → 775,15 |
if (radeon_encoder->audio && radeon_encoder->audio->dpms) |
radeon_encoder->audio->dpms(encoder, mode == DRM_MODE_DPMS_ON); |
} |
unsigned int radeon_audio_decode_dfs_div(unsigned int div) |
{ |
if (div >= 8 && div < 64) |
return (div - 8) * 25 + 200; |
else if (div >= 64 && div < 96) |
return (div - 64) * 50 + 1600; |
else if (div >= 96 && div < 128) |
return (div - 96) * 100 + 3200; |
else |
return 0; |
} |
/drivers/video/drm/radeon/radeon_audio.h |
---|
79,5 → 79,6 |
void radeon_audio_mode_set(struct drm_encoder *encoder, |
struct drm_display_mode *mode); |
void radeon_audio_dpms(struct drm_encoder *encoder, int mode); |
unsigned int radeon_audio_decode_dfs_div(unsigned int div); |
#endif |
/drivers/video/drm/radeon/radeon_connectors.c |
---|
1138,6 → 1138,10 |
if (!radeon_connector->dac_load_detect) |
return ret; |
r = pm_runtime_get_sync(connector->dev->dev); |
if (r < 0) |
return connector_status_disconnected; |
encoder = radeon_best_single_encoder(connector); |
if (!encoder) |
ret = connector_status_disconnected; |
1148,6 → 1152,8 |
if (ret == connector_status_connected) |
ret = radeon_connector_analog_encoder_conflict_solve(connector, encoder, ret, false); |
radeon_connector_update_scratch_regs(connector, ret); |
pm_runtime_mark_last_busy(connector->dev->dev); |
pm_runtime_put_autosuspend(connector->dev->dev); |
return ret; |
} |
1209,7 → 1215,15 |
enum drm_connector_status ret = connector_status_disconnected; |
bool dret = false, broken_edid = false; |
r = pm_runtime_get_sync(connector->dev->dev); |
if (r < 0) |
return connector_status_disconnected; |
if (radeon_connector->detected_hpd_without_ddc) { |
force = true; |
radeon_connector->detected_hpd_without_ddc = false; |
} |
if (!force && radeon_check_hpd_status_unchanged(connector)) { |
ret = connector->status; |
goto exit; |
1373,6 → 1387,9 |
} |
exit: |
pm_runtime_mark_last_busy(connector->dev->dev); |
pm_runtime_put_autosuspend(connector->dev->dev); |
return ret; |
} |
1621,6 → 1638,10 |
if (radeon_dig_connector->is_mst) |
return connector_status_disconnected; |
r = pm_runtime_get_sync(connector->dev->dev); |
if (r < 0) |
return connector_status_disconnected; |
if (!force && radeon_check_hpd_status_unchanged(connector)) { |
ret = connector->status; |
goto out; |
1706,6 → 1727,9 |
} |
out: |
pm_runtime_mark_last_busy(connector->dev->dev); |
pm_runtime_put_autosuspend(connector->dev->dev); |
return ret; |
} |
/drivers/video/drm/radeon/radeon_cs.c |
---|
34,13 → 34,6 |
#define RADEON_CS_MAX_PRIORITY 32u |
#define RADEON_CS_NUM_BUCKETS (RADEON_CS_MAX_PRIORITY + 1) |
static inline unsigned long |
copy_from_user(void *to, const void __user *from, unsigned long n) |
{ |
memcpy(to, from, n); |
return n; |
} |
/* This is based on the bucket sort with O(n) time complexity. |
* An item with priority "i" is added to bucket[i]. The lists are then |
* concatenated in descending order. |
/drivers/video/drm/radeon/radeon_display.c |
---|
1449,6 → 1449,15 |
* \param dev Device to query. |
* \param crtc Crtc to query. |
* \param flags Flags from caller (DRM_CALLED_FROM_VBLIRQ or 0). |
* For driver internal use only also supports these flags: |
* |
* USE_REAL_VBLANKSTART to use the real start of vblank instead |
* of a fudged earlier start of vblank. |
* |
* GET_DISTANCE_TO_VBLANKSTART to return distance to the |
* fudged earlier start of vblank in *vpos and the distance |
* to true start of vblank in *hpos. |
* |
* \param *vpos Location where vertical scanout position should be stored. |
* \param *hpos Location where horizontal scanout position should go. |
* \param *stime Target location for timestamp taken immediately before |
1592,10 → 1601,40 |
vbl_end = 0; |
} |
/* Called from driver internal vblank counter query code? */ |
if (flags & GET_DISTANCE_TO_VBLANKSTART) { |
/* Caller wants distance from real vbl_start in *hpos */ |
*hpos = *vpos - vbl_start; |
} |
/* Fudge vblank to start a few scanlines earlier to handle the |
* problem that vblank irqs fire a few scanlines before start |
* of vblank. Some driver internal callers need the true vblank |
* start to be used and signal this via the USE_REAL_VBLANKSTART flag. |
* |
* The cause of the "early" vblank irq is that the irq is triggered |
* by the line buffer logic when the line buffer read position enters |
* the vblank, whereas our crtc scanout position naturally lags the |
* line buffer read position. |
*/ |
if (!(flags & USE_REAL_VBLANKSTART)) |
vbl_start -= rdev->mode_info.crtcs[pipe]->lb_vblank_lead_lines; |
/* Test scanout position against vblank region. */ |
if ((*vpos < vbl_start) && (*vpos >= vbl_end)) |
in_vbl = false; |
/* In vblank? */ |
if (in_vbl) |
ret |= DRM_SCANOUTPOS_IN_VBLANK; |
/* Called from driver internal vblank counter query code? */ |
if (flags & GET_DISTANCE_TO_VBLANKSTART) { |
/* Caller wants distance from fudged earlier vbl_start */ |
*vpos -= vbl_start; |
return ret; |
} |
/* Check if inside vblank area and apply corrective offsets: |
* vpos will then be >=0 in video scanout area, but negative |
* within vblank area, counting down the number of lines until |
1611,31 → 1650,5 |
/* Correct for shifted end of vbl at vbl_end. */ |
*vpos = *vpos - vbl_end; |
/* In vblank? */ |
if (in_vbl) |
ret |= DRM_SCANOUTPOS_IN_VBLANK; |
/* Is vpos outside nominal vblank area, but less than |
* 1/100 of a frame height away from start of vblank? |
* If so, assume this isn't a massively delayed vblank |
* interrupt, but a vblank interrupt that fired a few |
* microseconds before true start of vblank. Compensate |
* by adding a full frame duration to the final timestamp. |
* Happens, e.g., on ATI R500, R600. |
* |
* We only do this if DRM_CALLED_FROM_VBLIRQ. |
*/ |
if ((flags & DRM_CALLED_FROM_VBLIRQ) && !in_vbl) { |
vbl_start = mode->crtc_vdisplay; |
vtotal = mode->crtc_vtotal; |
if (vbl_start - *vpos < vtotal / 100) { |
*vpos -= vtotal; |
/* Signal this correction as "applied". */ |
ret |= 0x8; |
} |
} |
return ret; |
} |
/drivers/video/drm/radeon/radeon_gart.c |
---|
29,7 → 29,7 |
#include <drm/radeon_drm.h> |
#include "radeon.h" |
#undef CONFIG_X86 |
void* pci_alloc_consistent(struct pci_dev *hwdev, size_t size, |
addr_t *dma_handle) |
{ |
/drivers/video/drm/radeon/radeon_pm.c |
---|
897,13 → 897,7 |
/* update display watermarks based on new power state */ |
radeon_bandwidth_update(rdev); |
/* update displays */ |
radeon_dpm_display_configuration_changed(rdev); |
rdev->pm.dpm.current_active_crtcs = rdev->pm.dpm.new_active_crtcs; |
rdev->pm.dpm.current_active_crtc_count = rdev->pm.dpm.new_active_crtc_count; |
rdev->pm.dpm.single_display = single_display; |
/* wait for the rings to drain */ |
for (i = 0; i < RADEON_NUM_RINGS; i++) { |
struct radeon_ring *ring = &rdev->ring[i]; |
919,6 → 913,13 |
radeon_dpm_post_set_power_state(rdev); |
/* update displays */ |
radeon_dpm_display_configuration_changed(rdev); |
rdev->pm.dpm.current_active_crtcs = rdev->pm.dpm.new_active_crtcs; |
rdev->pm.dpm.current_active_crtc_count = rdev->pm.dpm.new_active_crtc_count; |
rdev->pm.dpm.single_display = single_display; |
if (rdev->asic->dpm.force_performance_level) { |
if (rdev->pm.dpm.thermal_active) { |
enum radeon_dpm_forced_level level = rdev->pm.dpm.forced_level; |
/drivers/video/drm/radeon/radeon_sa.c |
---|
349,8 → 349,13 |
/* see if we can skip over some allocations */ |
} while (radeon_sa_bo_next_hole(sa_manager, fences, tries)); |
for (i = 0; i < RADEON_NUM_RINGS; ++i) |
radeon_fence_ref(fences[i]); |
spin_unlock(&sa_manager->wq.lock); |
r = radeon_fence_wait_any(rdev, fences, false); |
for (i = 0; i < RADEON_NUM_RINGS; ++i) |
radeon_fence_unref(&fences[i]); |
spin_lock(&sa_manager->wq.lock); |
/* if we have nothing to wait for block */ |
if (r == -ENOENT) { |
/drivers/video/drm/radeon/radeon_vm.c |
---|
455,7 → 455,7 |
if (soffset) { |
/* make sure object fit at this offset */ |
eoffset = soffset + size; |
eoffset = soffset + size - 1; |
if (soffset >= eoffset) { |
r = -EINVAL; |
goto error_unreserve; |
462,8 → 462,8 |
} |
last_pfn = eoffset / RADEON_GPU_PAGE_SIZE; |
if (last_pfn > rdev->vm_manager.max_pfn) { |
dev_err(rdev->dev, "va above limit (0x%08X > 0x%08X)\n", |
if (last_pfn >= rdev->vm_manager.max_pfn) { |
dev_err(rdev->dev, "va above limit (0x%08X >= 0x%08X)\n", |
last_pfn, rdev->vm_manager.max_pfn); |
r = -EINVAL; |
goto error_unreserve; |
478,7 → 478,7 |
eoffset /= RADEON_GPU_PAGE_SIZE; |
if (soffset || eoffset) { |
struct interval_tree_node *it; |
it = interval_tree_iter_first(&vm->va, soffset, eoffset - 1); |
it = interval_tree_iter_first(&vm->va, soffset, eoffset); |
if (it && it != &bo_va->it) { |
struct radeon_bo_va *tmp; |
tmp = container_of(it, struct radeon_bo_va, it); |
518,7 → 518,7 |
if (soffset || eoffset) { |
spin_lock(&vm->status_lock); |
bo_va->it.start = soffset; |
bo_va->it.last = eoffset - 1; |
bo_va->it.last = eoffset; |
list_add(&bo_va->vm_status, &vm->cleared); |
spin_unlock(&vm->status_lock); |
interval_tree_insert(&bo_va->it, &vm->va); |
888,7 → 888,7 |
unsigned i; |
start >>= radeon_vm_block_size; |
end >>= radeon_vm_block_size; |
end = (end - 1) >> radeon_vm_block_size; |
for (i = start; i <= end; ++i) |
radeon_bo_fence(vm->page_tables[i].bo, fence, true); |
/drivers/video/drm/radeon/rdisplay.c |
---|
3,7 → 3,7 |
#include <drm/radeon_drm.h> |
#include "radeon.h" |
#include "radeon_object.h" |
#include "bitmap.h" |
#include <display.h> |
#include "r100d.h" |
/drivers/video/drm/radeon/rdisplay_kms.c |
---|
5,7 → 5,6 |
#include "radeon_object.h" |
#include "drm_fb_helper.h" |
#include "hmm.h" |
#include "bitmap.h" |
#include <display.h> |
extern struct drm_framebuffer *main_fb; |
16,6 → 15,9 |
static cursor_t* __stdcall select_cursor_kms(cursor_t *cursor); |
static void __stdcall move_cursor_kms(cursor_t *cursor, int x, int y); |
extern int init_cursor(cursor_t *cursor); |
extern void __stdcall restore_cursor(int x, int y); |
int radeon_align_pitch(struct radeon_device *rdev, int width, int bpp, bool tiled); |
void disable_mouse(void); |
/drivers/video/drm/radeon/sid.h |
---|
915,6 → 915,11 |
#define DCCG_AUDIO_DTO1_PHASE 0x05c0 |
#define DCCG_AUDIO_DTO1_MODULE 0x05c4 |
#define DENTIST_DISPCLK_CNTL 0x0490 |
# define DENTIST_DPREFCLK_WDIVIDER(x) (((x) & 0x7f) << 24) |
# define DENTIST_DPREFCLK_WDIVIDER_MASK (0x7f << 24) |
# define DENTIST_DPREFCLK_WDIVIDER_SHIFT 24 |
#define AFMT_AUDIO_SRC_CONTROL 0x713c |
#define AFMT_AUDIO_SRC_SELECT(x) (((x) & 7) << 0) |
/* AFMT_AUDIO_SRC_SELECT |
/drivers/video/drm/radeon/utils.c |
---|
159,240 → 159,7 |
} |
//const char hex_asc[] = "0123456789abcdef"; |
/** |
* hex_to_bin - convert a hex digit to its real value |
* @ch: ascii character represents hex digit |
* |
* hex_to_bin() converts one hex digit to its actual value or -1 in case of bad |
* input. |
*/ |
int hex_to_bin(char ch) |
{ |
if ((ch >= '0') && (ch <= '9')) |
return ch - '0'; |
ch = tolower(ch); |
if ((ch >= 'a') && (ch <= 'f')) |
return ch - 'a' + 10; |
return -1; |
} |
EXPORT_SYMBOL(hex_to_bin); |
/** |
* hex2bin - convert an ascii hexadecimal string to its binary representation |
* @dst: binary result |
* @src: ascii hexadecimal string |
* @count: result length |
* |
* Return 0 on success, -1 in case of bad input. |
*/ |
int hex2bin(u8 *dst, const char *src, size_t count) |
{ |
while (count--) { |
int hi = hex_to_bin(*src++); |
int lo = hex_to_bin(*src++); |
if ((hi < 0) || (lo < 0)) |
return -1; |
*dst++ = (hi << 4) | lo; |
} |
return 0; |
} |
EXPORT_SYMBOL(hex2bin); |
/** |
* hex_dump_to_buffer - convert a blob of data to "hex ASCII" in memory |
* @buf: data blob to dump |
* @len: number of bytes in the @buf |
* @rowsize: number of bytes to print per line; must be 16 or 32 |
* @groupsize: number of bytes to print at a time (1, 2, 4, 8; default = 1) |
* @linebuf: where to put the converted data |
* @linebuflen: total size of @linebuf, including space for terminating NUL |
* @ascii: include ASCII after the hex output |
* |
* hex_dump_to_buffer() works on one "line" of output at a time, i.e., |
* 16 or 32 bytes of input data converted to hex + ASCII output. |
* |
* Given a buffer of u8 data, hex_dump_to_buffer() converts the input data |
* to a hex + ASCII dump at the supplied memory location. |
* The converted output is always NUL-terminated. |
* |
* E.g.: |
* hex_dump_to_buffer(frame->data, frame->len, 16, 1, |
* linebuf, sizeof(linebuf), true); |
* |
* example output buffer: |
* 40 41 42 43 44 45 46 47 48 49 4a 4b 4c 4d 4e 4f @ABCDEFGHIJKLMNO |
*/ |
int hex_dump_to_buffer(const void *buf, size_t len, int rowsize, int groupsize, |
char *linebuf, size_t linebuflen, bool ascii) |
{ |
const u8 *ptr = buf; |
int ngroups; |
u8 ch; |
int j, lx = 0; |
int ascii_column; |
int ret; |
if (rowsize != 16 && rowsize != 32) |
rowsize = 16; |
if (len > rowsize) /* limit to one line at a time */ |
len = rowsize; |
if (!is_power_of_2(groupsize) || groupsize > 8) |
groupsize = 1; |
if ((len % groupsize) != 0) /* no mixed size output */ |
groupsize = 1; |
ngroups = len / groupsize; |
ascii_column = rowsize * 2 + rowsize / groupsize + 1; |
if (!linebuflen) |
goto overflow1; |
if (!len) |
goto nil; |
if (groupsize == 8) { |
const u64 *ptr8 = buf; |
for (j = 0; j < ngroups; j++) { |
ret = snprintf(linebuf + lx, linebuflen - lx, |
"%s%16.16llx", j ? " " : "", |
(unsigned long long)*(ptr8 + j)); |
if (ret >= linebuflen - lx) |
goto overflow1; |
lx += ret; |
} |
} else if (groupsize == 4) { |
const u32 *ptr4 = buf; |
for (j = 0; j < ngroups; j++) { |
ret = snprintf(linebuf + lx, linebuflen - lx, |
"%s%8.8x", j ? " " : "", |
*(ptr4 + j)); |
if (ret >= linebuflen - lx) |
goto overflow1; |
lx += ret; |
} |
} else if (groupsize == 2) { |
const u16 *ptr2 = buf; |
for (j = 0; j < ngroups; j++) { |
ret = snprintf(linebuf + lx, linebuflen - lx, |
"%s%4.4x", j ? " " : "", |
*(ptr2 + j)); |
if (ret >= linebuflen - lx) |
goto overflow1; |
lx += ret; |
} |
} else { |
for (j = 0; j < len; j++) { |
if (linebuflen < lx + 3) |
goto overflow2; |
ch = ptr[j]; |
linebuf[lx++] = hex_asc_hi(ch); |
linebuf[lx++] = hex_asc_lo(ch); |
linebuf[lx++] = ' '; |
} |
if (j) |
lx--; |
} |
if (!ascii) |
goto nil; |
while (lx < ascii_column) { |
if (linebuflen < lx + 2) |
goto overflow2; |
linebuf[lx++] = ' '; |
} |
for (j = 0; j < len; j++) { |
if (linebuflen < lx + 2) |
goto overflow2; |
ch = ptr[j]; |
linebuf[lx++] = (isascii(ch) && isprint(ch)) ? ch : '.'; |
} |
nil: |
linebuf[lx] = '\0'; |
return lx; |
overflow2: |
linebuf[lx++] = '\0'; |
overflow1: |
return ascii ? ascii_column + len : (groupsize * 2 + 1) * ngroups - 1; |
} |
/** |
* print_hex_dump - print a text hex dump to syslog for a binary blob of data |
* @level: kernel log level (e.g. KERN_DEBUG) |
* @prefix_str: string to prefix each line with; |
* caller supplies trailing spaces for alignment if desired |
* @prefix_type: controls whether prefix of an offset, address, or none |
* is printed (%DUMP_PREFIX_OFFSET, %DUMP_PREFIX_ADDRESS, %DUMP_PREFIX_NONE) |
* @rowsize: number of bytes to print per line; must be 16 or 32 |
* @groupsize: number of bytes to print at a time (1, 2, 4, 8; default = 1) |
* @buf: data blob to dump |
* @len: number of bytes in the @buf |
* @ascii: include ASCII after the hex output |
* |
* Given a buffer of u8 data, print_hex_dump() prints a hex + ASCII dump |
* to the kernel log at the specified kernel log level, with an optional |
* leading prefix. |
* |
* print_hex_dump() works on one "line" of output at a time, i.e., |
* 16 or 32 bytes of input data converted to hex + ASCII output. |
* print_hex_dump() iterates over the entire input @buf, breaking it into |
* "line size" chunks to format and print. |
* |
* E.g.: |
* print_hex_dump(KERN_DEBUG, "raw data: ", DUMP_PREFIX_ADDRESS, |
* 16, 1, frame->data, frame->len, true); |
* |
* Example output using %DUMP_PREFIX_OFFSET and 1-byte mode: |
* 0009ab42: 40 41 42 43 44 45 46 47 48 49 4a 4b 4c 4d 4e 4f @ABCDEFGHIJKLMNO |
* Example output using %DUMP_PREFIX_ADDRESS and 4-byte mode: |
* ffffffff88089af0: 73727170 77767574 7b7a7978 7f7e7d7c pqrstuvwxyz{|}~. |
*/ |
void print_hex_dump(const char *level, const char *prefix_str, int prefix_type, |
int rowsize, int groupsize, |
const void *buf, size_t len, bool ascii) |
{ |
const u8 *ptr = buf; |
int i, linelen, remaining = len; |
unsigned char linebuf[32 * 3 + 2 + 32 + 1]; |
if (rowsize != 16 && rowsize != 32) |
rowsize = 16; |
for (i = 0; i < len; i += rowsize) { |
linelen = min(remaining, rowsize); |
remaining -= rowsize; |
hex_dump_to_buffer(ptr + i, linelen, rowsize, groupsize, |
linebuf, sizeof(linebuf), ascii); |
switch (prefix_type) { |
case DUMP_PREFIX_ADDRESS: |
printk("%s%s%p: %s\n", |
level, prefix_str, ptr + i, linebuf); |
break; |
case DUMP_PREFIX_OFFSET: |
printk("%s%s%.8x: %s\n", level, prefix_str, i, linebuf); |
break; |
default: |
printk("%s%s%s\n", level, prefix_str, linebuf); |
break; |
} |
} |
} |
void print_hex_dump_bytes(const char *prefix_str, int prefix_type, |
const void *buf, size_t len) |
{ |
print_hex_dump(KERN_DEBUG, prefix_str, prefix_type, 16, 1, |
buf, len, true); |
} |
#define KMAP_MAX 256 |
static struct mutex kmap_mutex; |
1119,3 → 886,8 |
return b; |
} |
void vfree(const void *addr) |
{ |
KernelFree(addr); |
} |
/drivers/video/drm/radeon/vce_v1_0.c |
---|
178,12 → 178,12 |
return -EINVAL; |
} |
for (i = 0; i < sign->num; ++i) { |
if (sign->val[i].chip_id == chip_id) |
for (i = 0; i < le32_to_cpu(sign->num); ++i) { |
if (le32_to_cpu(sign->val[i].chip_id) == chip_id) |
break; |
} |
if (i == sign->num) |
if (i == le32_to_cpu(sign->num)) |
return -EINVAL; |
data += (256 - 64) / 4; |
191,18 → 191,18 |
data[1] = sign->val[i].nonce[1]; |
data[2] = sign->val[i].nonce[2]; |
data[3] = sign->val[i].nonce[3]; |
data[4] = sign->len + 64; |
data[4] = cpu_to_le32(le32_to_cpu(sign->len) + 64); |
memset(&data[5], 0, 44); |
memcpy(&data[16], &sign[1], rdev->vce_fw->size - sizeof(*sign)); |
data += data[4] / 4; |
data += le32_to_cpu(data[4]) / 4; |
data[0] = sign->val[i].sigval[0]; |
data[1] = sign->val[i].sigval[1]; |
data[2] = sign->val[i].sigval[2]; |
data[3] = sign->val[i].sigval[3]; |
rdev->vce.keyselect = sign->val[i].keyselect; |
rdev->vce.keyselect = le32_to_cpu(sign->val[i].keyselect); |
return 0; |
} |
/drivers/video/drm/ttm/ttm_tt.c |
---|
47,6 → 47,7 |
#include <drm/ttm/ttm_placement.h> |
#include <drm/ttm/ttm_page_alloc.h> |
#undef CONFIG_X86 |
/** |
* Allocates storage for pointers to the pages that back the ttm. |
*/ |