* Now using Thomas memory manager to manage the graphics memory; allocation
of graphics memory is now possible. * Changed driver name to start with "intel_extreme" to have a nicer device name. * Renamed frame_buffer* stuff to graphics_memory* as the frame buffer just happens to be located somewhere in the graphics memory. git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@17224 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
@@ -9,6 +9,8 @@
|
||||
#define INTEL_EXTREME_H
|
||||
|
||||
|
||||
#include <memory_manager.h>
|
||||
|
||||
#include <Accelerant.h>
|
||||
#include <Drivers.h>
|
||||
#include <PCI.h>
|
||||
@@ -45,13 +47,14 @@ struct intel_shared_info {
|
||||
uint32 bytes_per_row;
|
||||
uint32 dpms_mode;
|
||||
|
||||
area_id registers_area; // area of memory mapped registers
|
||||
area_id frame_buffer_area; // area of frame buffer
|
||||
uint8 *frame_buffer; // pointer to frame buffer (visible by all apps!)
|
||||
uint8 *physical_frame_buffer;
|
||||
|
||||
area_id registers_area; // area of memory mapped registers
|
||||
area_id graphics_memory_area;
|
||||
uint8 *graphics_memory;
|
||||
uint8 *physical_graphics_memory;
|
||||
uint32 graphics_memory_size;
|
||||
|
||||
uint32 frame_buffer_offset;
|
||||
|
||||
uint32 device_type;
|
||||
char device_identifier[32];
|
||||
struct pll_info pll_info;
|
||||
@@ -66,8 +69,9 @@ struct intel_info {
|
||||
area_id registers_area;
|
||||
struct intel_shared_info *shared_info;
|
||||
area_id shared_area;
|
||||
uint8 *frame_buffer;
|
||||
area_id frame_buffer_area;
|
||||
uint8 *graphics_memory;
|
||||
area_id graphics_memory_area;
|
||||
mem_info *memory_manager;
|
||||
|
||||
const char *device_identifier;
|
||||
uint32 device_type;
|
||||
@@ -83,8 +87,8 @@ enum {
|
||||
INTEL_GET_PRIVATE_DATA = B_DEVICE_OP_CODES_END + 1,
|
||||
|
||||
INTEL_GET_DEVICE_NAME,
|
||||
INTEL_ALLOC_LOCAL_MEMORY,
|
||||
INTEL_FREE_LOCAL_MEMORY
|
||||
INTEL_ALLOCATE_GRAPHICS_MEMORY,
|
||||
INTEL_FREE_GRAPHICS_MEMORY
|
||||
};
|
||||
|
||||
// retrieve the area_id of the kernel/accelerant shared info
|
||||
@@ -97,7 +101,7 @@ struct intel_get_private_data {
|
||||
struct intel_allocate_graphics_memory {
|
||||
uint32 magic;
|
||||
uint32 size;
|
||||
uint32 fb_offset;
|
||||
uint32 buffer_offset;
|
||||
uint32 handle;
|
||||
};
|
||||
|
||||
|
||||
@@ -11,6 +11,7 @@ Addon intel_extreme.accelerant : accelerants :
|
||||
dpms.cpp
|
||||
engine.cpp
|
||||
hooks.cpp
|
||||
memory.cpp
|
||||
mode.cpp
|
||||
: false
|
||||
: be
|
||||
|
||||
@@ -22,6 +22,8 @@ typedef struct accelerant_info {
|
||||
display_mode *mode_list; // cloned list of standard display modes
|
||||
area_id mode_list_area;
|
||||
|
||||
uint32 frame_buffer_handle;
|
||||
|
||||
int device;
|
||||
bool is_clone;
|
||||
} accelerant_info;
|
||||
@@ -50,4 +52,8 @@ extern void set_display_power_mode(uint32 mode);
|
||||
// modes.cpp
|
||||
extern status_t create_mode_list(void);
|
||||
|
||||
// memory.cpp
|
||||
extern void intel_free_memory(uint32 handle);
|
||||
extern status_t intel_allocate_memory(size_t size, uint32& handle, uint32& offset);
|
||||
|
||||
#endif /* INTEL_EXTREME_ACCELERANT_H */
|
||||
|
||||
@@ -32,7 +32,7 @@ enable_display_plane(bool enable)
|
||||
// when disabling it, we have to trigger the update using a write to
|
||||
// the display base address
|
||||
write32(INTEL_DISPLAY_CONTROL, oldValue & ~DISPLAY_CONTROL_ENABLED);
|
||||
write32(INTEL_DISPLAY_BASE, 0);
|
||||
write32(INTEL_DISPLAY_BASE, gInfo->shared_info->frame_buffer_offset);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -23,7 +23,7 @@ extern "C" void _sPrintf(const char *format, ...);
|
||||
static engine_token sEngineToken = {1, 0 /*B_2D_ACCELERATION*/, NULL};
|
||||
|
||||
|
||||
// public function: return number of hardware engine
|
||||
/** Return number of hardware engines */
|
||||
|
||||
uint32
|
||||
intel_accelerant_engine_count(void)
|
||||
|
||||
@@ -0,0 +1,54 @@
|
||||
/*
|
||||
* Copyright 2006, Haiku, Inc. All Rights Reserved.
|
||||
* Distributed under the terms of the MIT License.
|
||||
*
|
||||
* Authors:
|
||||
* Axel Dörfler, [email protected]
|
||||
*/
|
||||
|
||||
|
||||
#include "accelerant.h"
|
||||
#include "intel_extreme.h"
|
||||
|
||||
#include <errno.h>
|
||||
|
||||
|
||||
//#define TRACE_MEMORY
|
||||
#ifdef TRACE_MEMORY
|
||||
extern "C" void _sPrintf(const char *format, ...);
|
||||
# define TRACE(x) _sPrintf x
|
||||
#else
|
||||
# define TRACE(x) ;
|
||||
#endif
|
||||
|
||||
|
||||
void
|
||||
intel_free_memory(uint32 handle)
|
||||
{
|
||||
if (!handle)
|
||||
return;
|
||||
|
||||
intel_free_graphics_memory freeMemory;
|
||||
freeMemory.magic = INTEL_PRIVATE_DATA_MAGIC;
|
||||
freeMemory.handle = handle;
|
||||
|
||||
ioctl(gInfo->device, INTEL_FREE_GRAPHICS_MEMORY, &freeMemory, sizeof(freeMemory));
|
||||
}
|
||||
|
||||
|
||||
status_t
|
||||
intel_allocate_memory(size_t size, uint32& handle, uint32& offset)
|
||||
{
|
||||
intel_allocate_graphics_memory allocMemory;
|
||||
allocMemory.magic = INTEL_PRIVATE_DATA_MAGIC;
|
||||
allocMemory.size = size;
|
||||
|
||||
if (ioctl(gInfo->device, INTEL_ALLOCATE_GRAPHICS_MEMORY, &allocMemory, sizeof(allocMemory)) < 0)
|
||||
return errno;
|
||||
|
||||
handle = allocMemory.handle;
|
||||
offset = allocMemory.buffer_offset;
|
||||
|
||||
return B_OK;
|
||||
}
|
||||
|
||||
@@ -12,7 +12,7 @@
|
||||
#include "utility.h"
|
||||
|
||||
|
||||
//#define TRACE_MODE
|
||||
#define TRACE_MODE
|
||||
#ifdef TRACE_MODE
|
||||
extern "C" void _sPrintf(const char *format, ...);
|
||||
# define TRACE(x) _sPrintf x
|
||||
@@ -228,6 +228,8 @@ intel_set_display_mode(display_mode *mode)
|
||||
{
|
||||
TRACE(("intel_set_display_mode()\n"));
|
||||
|
||||
// TODO: locking!
|
||||
|
||||
if (mode == NULL)
|
||||
return B_BAD_VALUE;
|
||||
|
||||
@@ -238,6 +240,26 @@ intel_set_display_mode(display_mode *mode)
|
||||
uint32 colorMode, bytesPerRow;
|
||||
get_color_space_format(current, colorMode, bytesPerRow);
|
||||
|
||||
// free old and allocate new frame buffer in graphics memory
|
||||
|
||||
intel_free_memory(gInfo->frame_buffer_handle);
|
||||
|
||||
uint32 offset;
|
||||
if (intel_allocate_memory(bytesPerRow * current.timing.v_display,
|
||||
gInfo->frame_buffer_handle, offset) < B_OK) {
|
||||
// oh, how did that happen? Unfortunately, there is no really good way back
|
||||
if (intel_allocate_memory(gInfo->shared_info->current_mode.timing.v_display
|
||||
* gInfo->shared_info->bytes_per_row, gInfo->frame_buffer_handle,
|
||||
offset) == B_OK) {
|
||||
gInfo->shared_info->frame_buffer_offset = offset;
|
||||
write32(INTEL_DISPLAY_BASE, offset);
|
||||
}
|
||||
|
||||
return B_NO_MEMORY;
|
||||
}
|
||||
|
||||
gInfo->shared_info->frame_buffer_offset = offset;
|
||||
|
||||
// update timing parameters
|
||||
|
||||
write32(INTEL_DISPLAY_HTOTAL, ((uint32)(current.timing.h_total - 1) << 16)
|
||||
@@ -288,7 +310,7 @@ intel_set_display_mode(display_mode *mode)
|
||||
|
||||
// changing bytes per row seems to be ignored if the plane/pipe is turned off
|
||||
write32(INTEL_DISPLAY_BYTES_PER_ROW, bytesPerRow);
|
||||
write32(INTEL_DISPLAY_BASE, 0);
|
||||
write32(INTEL_DISPLAY_BASE, gInfo->shared_info->frame_buffer_offset);
|
||||
// triggers writing back double-buffered registers
|
||||
|
||||
// update shared info
|
||||
@@ -313,8 +335,10 @@ intel_get_frame_buffer_config(frame_buffer_config *config)
|
||||
{
|
||||
TRACE(("intel_get_frame_buffer_config()\n"));
|
||||
|
||||
config->frame_buffer = gInfo->shared_info->frame_buffer;
|
||||
config->frame_buffer_dma = gInfo->shared_info->physical_frame_buffer;
|
||||
uint32 offset = gInfo->shared_info->frame_buffer_offset;
|
||||
|
||||
config->frame_buffer = gInfo->shared_info->graphics_memory + offset;
|
||||
config->frame_buffer_dma = gInfo->shared_info->physical_graphics_memory + offset;
|
||||
config->bytes_per_row = gInfo->shared_info->bytes_per_row;
|
||||
|
||||
return B_OK;
|
||||
|
||||
@@ -12,6 +12,8 @@ KernelAddon intel_extreme : kernel drivers bin :
|
||||
intel_extreme.cpp
|
||||
|
||||
kernel_cpp.cpp
|
||||
|
||||
: libgraphicscommon.a
|
||||
;
|
||||
|
||||
SEARCH on [ FGristFiles
|
||||
|
||||
@@ -181,28 +181,48 @@ device_ioctl(void *data, uint32 op, void *buffer, size_t bufferLength)
|
||||
#endif
|
||||
return B_OK;
|
||||
|
||||
/*
|
||||
// graphics mem manager
|
||||
case INTEL_ALLOC_LOCAL_MEMORY:
|
||||
case INTEL_ALLOCATE_GRAPHICS_MEMORY:
|
||||
{
|
||||
intel_alloc_local_mem *allocMemory = (intel_alloc_local_mem *)buffer;
|
||||
intel_allocate_graphics_memory allocMemory;
|
||||
#ifdef __HAIKU__
|
||||
if (user_memcpy(&allocMemory, buffer, sizeof(intel_allocate_graphics_memory)) < B_OK)
|
||||
return B_BAD_ADDRESS;
|
||||
#else
|
||||
memcpy(&allocMemory, buffer, sizeof(intel_allocate_graphics_memory));
|
||||
#endif
|
||||
|
||||
if (allocMemory->magic == INTEL_PRIVATE_DATA_MAGIC) {
|
||||
return mem_alloc(di->local_memmgr, allocMemory->size, dev,
|
||||
&allocMemory->handle, &am->fb_offset);
|
||||
if (allocMemory.magic != INTEL_PRIVATE_DATA_MAGIC)
|
||||
return B_BAD_VALUE;
|
||||
|
||||
status_t status = mem_alloc(info->memory_manager, allocMemory.size, info,
|
||||
&allocMemory.handle, &allocMemory.buffer_offset);
|
||||
if (status == B_OK) {
|
||||
// copy result
|
||||
#ifdef __HAIKU__
|
||||
if (user_memcpy(buffer, &allocMemory, sizeof(intel_allocate_graphics_memory)) < B_OK)
|
||||
return B_BAD_ADDRESS;
|
||||
#else
|
||||
memcpy(buffer, &allocMemory, sizeof(intel_allocate_graphics_memory));
|
||||
#endif
|
||||
}
|
||||
break;
|
||||
return status;
|
||||
}
|
||||
|
||||
case INTEL_FREE_LOCAL_MEMORY:
|
||||
case INTEL_FREE_GRAPHICS_MEMORY:
|
||||
{
|
||||
intel_free_local_mem *freeMemory = (intel_free_local_mem *)buffer;
|
||||
intel_free_graphics_memory freeMemory;
|
||||
#ifdef __HAIKU__
|
||||
if (user_memcpy(&freeMemory, buffer, sizeof(intel_free_graphics_memory)) < B_OK)
|
||||
return B_BAD_ADDRESS;
|
||||
#else
|
||||
memcpy(&freeMemory, buffer, sizeof(intel_free_graphics_memory));
|
||||
#endif
|
||||
|
||||
if (freeMemory->magic == INTEL_PRIVATE_DATA_MAGIC)
|
||||
return mem_free(di->local_memmgr, freeMemory->handle, dev);
|
||||
if (freeMemory.magic == INTEL_PRIVATE_DATA_MAGIC)
|
||||
return mem_free(info->memory_manager, freeMemory.handle, info);
|
||||
break;
|
||||
}
|
||||
*/
|
||||
|
||||
default:
|
||||
TRACE((DEVICE_NAME ": ioctl() unknown message %ld (length = %ld)\n",
|
||||
|
||||
@@ -137,8 +137,7 @@ init_driver(void)
|
||||
// create device names & allocate device info structure
|
||||
|
||||
char name[64];
|
||||
sprintf(name, "graphics/%04X_%04X_%02X%02X%02X",
|
||||
info->vendor_id, info->device_id,
|
||||
sprintf(name, "graphics/intel_extreme_%02x%02x%02x",
|
||||
info->bus, info->device,
|
||||
info->function);
|
||||
|
||||
|
||||
@@ -90,23 +90,23 @@ intel_extreme_init(intel_info &info)
|
||||
|
||||
// map frame buffer, try to map it write combined
|
||||
|
||||
PhysicalMemoryMapper fbMapper;
|
||||
info.frame_buffer_area = fbMapper.Map("intel extreme frame buffer",
|
||||
PhysicalMemoryMapper graphicsMapper;
|
||||
info.graphics_memory_area = graphicsMapper.Map("intel extreme graphics memory",
|
||||
(void *)info.pci->u.h0.base_registers[0],
|
||||
memorySize, B_ANY_KERNEL_BLOCK_ADDRESS | B_MTR_WC,
|
||||
B_READ_AREA | B_WRITE_AREA, (void **)&info.frame_buffer);
|
||||
if (fbMapper.InitCheck() < B_OK) {
|
||||
B_READ_AREA | B_WRITE_AREA, (void **)&info.graphics_memory);
|
||||
if (graphicsMapper.InitCheck() < B_OK) {
|
||||
// try again without write combining
|
||||
dprintf(DEVICE_NAME ": enabling write combined mode failed.\n");
|
||||
|
||||
info.frame_buffer_area = fbMapper.Map("intel extreme frame buffer",
|
||||
info.graphics_memory_area = graphicsMapper.Map("intel extreme graphics memory",
|
||||
(void *)info.pci->u.h0.base_registers[0],
|
||||
memorySize/*info.pci->u.h0.base_register_sizes[0]*/, B_ANY_KERNEL_BLOCK_ADDRESS,
|
||||
B_READ_AREA | B_WRITE_AREA, (void **)&info.frame_buffer);
|
||||
B_READ_AREA | B_WRITE_AREA, (void **)&info.graphics_memory);
|
||||
}
|
||||
if (fbMapper.InitCheck() < B_OK) {
|
||||
if (graphicsMapper.InitCheck() < B_OK) {
|
||||
dprintf(DEVICE_NAME ": could not map frame buffer!\n");
|
||||
return info.frame_buffer_area;
|
||||
return info.graphics_memory_area;
|
||||
}
|
||||
|
||||
// memory mapped I/O
|
||||
@@ -123,16 +123,24 @@ intel_extreme_init(intel_info &info)
|
||||
return info.registers_area;
|
||||
}
|
||||
|
||||
// init graphics memory manager
|
||||
|
||||
info.memory_manager = mem_init("intel extreme memory manager", 0, memorySize, 1024,
|
||||
min_c(memorySize / 1024, 512));
|
||||
if (info.memory_manager == NULL)
|
||||
return B_NO_MEMORY;
|
||||
|
||||
// no errors, so keep mappings
|
||||
fbMapper.Keep();
|
||||
graphicsMapper.Keep();
|
||||
mmioMapper.Keep();
|
||||
|
||||
info.shared_info->frame_buffer_area = info.frame_buffer_area;
|
||||
info.shared_info->graphics_memory_area = info.graphics_memory_area;
|
||||
info.shared_info->registers_area = info.registers_area;
|
||||
info.shared_info->frame_buffer = info.frame_buffer;
|
||||
info.shared_info->physical_frame_buffer = (uint8 *)info.pci->u.h0.base_registers[0];
|
||||
info.shared_info->graphics_memory = info.graphics_memory;
|
||||
info.shared_info->physical_graphics_memory = (uint8 *)info.pci->u.h0.base_registers[0];
|
||||
|
||||
info.shared_info->graphics_memory_size = memorySize;
|
||||
info.shared_info->frame_buffer_offset = 0;
|
||||
info.shared_info->dpms_mode = B_DPMS_ON;
|
||||
info.shared_info->pll_info.reference_frequency = 48000; // 48 kHz
|
||||
info.shared_info->pll_info.min_frequency = 25000; // 25 MHz (not tested)
|
||||
@@ -161,7 +169,9 @@ intel_extreme_uninit(intel_info &info)
|
||||
{
|
||||
dprintf(DEVICE_NAME": intel_extreme_uninit()\n");
|
||||
|
||||
delete_area(info.frame_buffer_area);
|
||||
mem_destroy(info.memory_manager);
|
||||
|
||||
delete_area(info.graphics_memory_area);
|
||||
delete_area(info.registers_area);
|
||||
delete_area(info.shared_area);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user