* Now allocates space for the hardware status page and cursor memory, not yet

used, though.
* Renamed the PhyisicalPageMapper class to AreaKeeper and made it a bit more
  generic (ie. it can now also create usual areas)
* The shared_info is now created using the AreaKeeper, too, and this actually
  fixes some potential memory leaks.


git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@17412 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
Axel Dörfler 2006-05-10 12:37:27 +00:00
parent 96451fe133
commit 08ef16abee
4 changed files with 96 additions and 45 deletions

View File

@ -34,20 +34,20 @@ enum {
// info about PLL on graphics card // info about PLL on graphics card
struct pll_info { struct pll_info {
uint32 reference_frequency; uint32 reference_frequency;
uint32 max_frequency; uint32 max_frequency;
uint32 min_frequency; uint32 min_frequency;
uint32 divisor_register; uint32 divisor_register;
}; };
struct ring_buffer { struct ring_buffer {
struct lock lock; struct lock lock;
uint32 register_base; uint32 register_base;
uint32 handle; uint32 handle;
uint32 offset; uint32 offset;
uint32 size; uint32 size;
uint32 position; uint32 position;
uint8 *base; uint8 *base;
}; };
struct overlay_registers; struct overlay_registers;
@ -62,6 +62,8 @@ struct intel_shared_info {
uint32 dpms_mode; uint32 dpms_mode;
area_id registers_area; // area of memory mapped registers area_id registers_area; // area of memory mapped registers
uint8 *physical_status_page;
uint8 *physical_cursor_memory;
area_id graphics_memory_area; area_id graphics_memory_area;
uint8 *graphics_memory; uint8 *graphics_memory;
uint8 *physical_graphics_memory; uint8 *physical_graphics_memory;
@ -83,24 +85,24 @@ struct intel_shared_info {
}; };
struct intel_info { struct intel_info {
uint32 cookie_magic; uint32 cookie_magic;
int32 open_count; int32 open_count;
int32 id; int32 id;
pci_info *pci; pci_info *pci;
uint8 *registers; uint8 *registers;
area_id registers_area; area_id registers_area;
struct intel_shared_info *shared_info; struct intel_shared_info *shared_info;
area_id shared_area; area_id shared_area;
struct overlay_registers *overlay_registers; struct overlay_registers *overlay_registers;
// update buffer, shares an area with shared_info // update buffer, shares an area with shared_info
uint8 *graphics_memory; uint8 *graphics_memory;
area_id graphics_memory_area; area_id graphics_memory_area;
mem_info *memory_manager; mem_info *memory_manager;
const char *device_identifier; const char *device_identifier;
uint32 device_type; uint32 device_type;
}; };
//----------------- ioctl() interface ---------------- //----------------- ioctl() interface ----------------
@ -413,6 +415,19 @@ struct overlay_registers {
uint16 horizontal_coefficients_uv[128]; uint16 horizontal_coefficients_uv[128];
}; };
struct hardware_status {
uint32 interrupt_status_register;
uint32 _reserved0[3];
void *primary_ring_head_storage;
uint32 _reserved1[3];
void *secondary_ring_0_head_storage;
void *secondary_ring_1_head_storage;
uint32 _reserved2[2];
void *binning_head_storage;
uint32 _reserved3[3];
uint32 store[1008];
};
//---------------------------------------------------------- //----------------------------------------------------------
extern status_t intel_extreme_init(intel_info &info); extern status_t intel_extreme_init(intel_info &info);

View File

@ -131,8 +131,13 @@ init_common(int device, bool isClone)
sharedCloner.Keep(); sharedCloner.Keep();
regsCloner.Keep(); regsCloner.Keep();
// The overlay registers, hardware status, and cursor memory share
// a single area with the shared_info
gInfo->overlay_registers = (struct overlay_registers *)((uint8 *)gInfo->shared_info gInfo->overlay_registers = (struct overlay_registers *)((uint8 *)gInfo->shared_info
+ ROUND_TO_PAGE_SIZE(sizeof(intel_shared_info))); + ROUND_TO_PAGE_SIZE(sizeof(intel_shared_info)));
gInfo->status = (hardware_status *)((uint8 *)gInfo->overlay_registers + B_PAGE_SIZE);
gInfo->cursor_memory = (uint8 *)gInfo->overlay_registers + 2 * B_PAGE_SIZE;
return B_OK; return B_OK;
} }

View File

@ -47,6 +47,9 @@ struct accelerant_info {
uint32 last_vertical_overlay_scale; uint32 last_vertical_overlay_scale;
uint32 overlay_position_buffer_offset; uint32 overlay_position_buffer_offset;
hardware_status *status;
uint8 *cursor_memory;
int device; int device;
bool is_clone; bool is_clone;
}; };

View File

@ -19,46 +19,59 @@
#include <errno.h> #include <errno.h>
class PhysicalMemoryMapper { class AreaKeeper {
public: public:
PhysicalMemoryMapper(); AreaKeeper();
~PhysicalMemoryMapper(); ~AreaKeeper();
area_id Create(const char *name, void **_virtualAddress, uint32 spec,
size_t size, uint32 lock, uint32 protection);
area_id Map(const char *name, void *physicalAddress, size_t numBytes, area_id Map(const char *name, void *physicalAddress, size_t numBytes,
uint32 spec, uint32 protection, void **virtualAddress); uint32 spec, uint32 protection, void **_virtualAddress);
status_t InitCheck() { return fArea < B_OK ? (status_t)fArea : B_OK; } status_t InitCheck() { return fArea < B_OK ? (status_t)fArea : B_OK; }
void Keep(); void Detach();
private: private:
area_id fArea; area_id fArea;
}; };
PhysicalMemoryMapper::PhysicalMemoryMapper() AreaKeeper::AreaKeeper()
: :
fArea(-1) fArea(-1)
{ {
} }
PhysicalMemoryMapper::~PhysicalMemoryMapper() AreaKeeper::~AreaKeeper()
{ {
if (fArea >= B_OK) if (fArea >= B_OK)
delete_area(fArea); delete_area(fArea);
} }
area_id area_id
PhysicalMemoryMapper::Map(const char *name, void *physicalAddress, size_t numBytes, AreaKeeper::Create(const char *name, void **_virtualAddress, uint32 spec,
uint32 spec, uint32 protection, void **virtualAddress) size_t size, uint32 lock, uint32 protection)
{ {
fArea = map_physical_memory(name, physicalAddress, numBytes, spec, protection, virtualAddress); fArea = create_area(name, _virtualAddress, spec, size, lock, protection);
return fArea; return fArea;
} }
void area_id
PhysicalMemoryMapper::Keep() AreaKeeper::Map(const char *name, void *physicalAddress, size_t numBytes,
uint32 spec, uint32 protection, void **_virtualAddress)
{
fArea = map_physical_memory(name, physicalAddress, numBytes, spec, protection,
_virtualAddress);
return fArea;
}
void
AreaKeeper::Detach()
{ {
fArea = -1; fArea = -1;
} }
@ -84,9 +97,10 @@ init_overlay_registers(overlay_registers *registers)
status_t status_t
intel_extreme_init(intel_info &info) intel_extreme_init(intel_info &info)
{ {
info.shared_area = create_area("intel extreme shared info", AreaKeeper sharedCreator;
info.shared_area = sharedCreator.Create("intel extreme shared info",
(void **)&info.shared_info, B_ANY_KERNEL_ADDRESS, (void **)&info.shared_info, B_ANY_KERNEL_ADDRESS,
ROUND_TO_PAGE_SIZE(sizeof(intel_shared_info)) + B_PAGE_SIZE, ROUND_TO_PAGE_SIZE(sizeof(intel_shared_info)) + 3 * B_PAGE_SIZE,
B_FULL_LOCK, 0); B_FULL_LOCK, 0);
if (info.shared_area < B_OK) if (info.shared_area < B_OK)
return info.shared_area; return info.shared_area;
@ -120,11 +134,11 @@ intel_extreme_init(intel_info &info)
memorySize *= 64; memorySize *= 64;
break; break;
} }
dprintf("detected %ld MB of stolen memory\n", memorySize / 1024 / 1024); dprintf(DEVICE_NAME ": detected %ld MB of stolen memory\n", memorySize / 1024 / 1024);
// map frame buffer, try to map it write combined // map frame buffer, try to map it write combined
PhysicalMemoryMapper graphicsMapper; AreaKeeper graphicsMapper;
info.graphics_memory_area = graphicsMapper.Map("intel extreme graphics memory", info.graphics_memory_area = graphicsMapper.Map("intel extreme graphics memory",
(void *)info.pci->u.h0.base_registers[0], (void *)info.pci->u.h0.base_registers[0],
memorySize, B_ANY_KERNEL_BLOCK_ADDRESS | B_MTR_WC, memorySize, B_ANY_KERNEL_BLOCK_ADDRESS | B_MTR_WC,
@ -145,7 +159,7 @@ intel_extreme_init(intel_info &info)
// memory mapped I/O // memory mapped I/O
PhysicalMemoryMapper mmioMapper; AreaKeeper mmioMapper;
info.registers_area = mmioMapper.Map("intel extreme mmio", info.registers_area = mmioMapper.Map("intel extreme mmio",
(void *)info.pci->u.h0.base_registers[1], (void *)info.pci->u.h0.base_registers[1],
info.pci->u.h0.base_register_sizes[1], info.pci->u.h0.base_register_sizes[1],
@ -157,6 +171,8 @@ intel_extreme_init(intel_info &info)
return info.registers_area; return info.registers_area;
} }
dprintf(DEVICE_NAME ": page table control %08lx\n", read32(INTEL_PAGE_TABLE_CONTROL));
// init graphics memory manager // init graphics memory manager
info.memory_manager = mem_init("intel extreme memory manager", 0, memorySize, 1024, info.memory_manager = mem_init("intel extreme memory manager", 0, memorySize, 1024,
@ -184,9 +200,10 @@ intel_extreme_init(intel_info &info)
secondary.base = info.graphics_memory + secondary.offset; secondary.base = info.graphics_memory + secondary.offset;
} }
// no errors, so keep mappings // no errors, so keep areas and mappings
graphicsMapper.Keep(); sharedCreator.Detach();
mmioMapper.Keep(); graphicsMapper.Detach();
mmioMapper.Detach();
info.shared_info->graphics_memory_area = info.graphics_memory_area; info.shared_info->graphics_memory_area = info.graphics_memory_area;
info.shared_info->registers_area = info.registers_area; info.shared_info->registers_area = info.registers_area;
@ -210,7 +227,7 @@ intel_extreme_init(intel_info &info)
#endif #endif
// setup overlay registers // setup overlay registers
info.overlay_registers = (overlay_registers *)((uint8 *)info.shared_info info.overlay_registers = (overlay_registers *)((uint8 *)info.shared_info
+ ROUND_TO_PAGE_SIZE(sizeof(intel_shared_info))); + ROUND_TO_PAGE_SIZE(sizeof(intel_shared_info)));
init_overlay_registers(info.overlay_registers); init_overlay_registers(info.overlay_registers);
@ -219,6 +236,17 @@ intel_extreme_init(intel_info &info)
get_memory_map(info.overlay_registers, sizeof(overlay_registers), &physicalEntry, 1); get_memory_map(info.overlay_registers, sizeof(overlay_registers), &physicalEntry, 1);
info.shared_info->physical_overlay_registers = (uint8 *)physicalEntry.address; info.shared_info->physical_overlay_registers = (uint8 *)physicalEntry.address;
// The hardware status page and the cursor memory share one area with
// the overlay registers and the shared info
get_memory_map((uint8 *)info.overlay_registers + B_PAGE_SIZE,
B_PAGE_SIZE, &physicalEntry, 1);
info.shared_info->physical_status_page = (uint8 *)physicalEntry.address;
get_memory_map((uint8 *)info.overlay_registers + 2 * B_PAGE_SIZE,
B_PAGE_SIZE, &physicalEntry, 1);
info.shared_info->physical_cursor_memory = (uint8 *)physicalEntry.address;
info.cookie_magic = INTEL_COOKIE_MAGIC; info.cookie_magic = INTEL_COOKIE_MAGIC;
// this makes the cookie valid to be used // this makes the cookie valid to be used