[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Qemu-ppc] [PATCH v5] Add resolutions via the command-line
From: |
G 3 |
Subject: |
[Qemu-ppc] [PATCH v5] Add resolutions via the command-line |
Date: |
Sun, 2 Oct 2016 18:22:03 -0400 |
Add the ability to add resolutions from the command-line. This patch
works by
looking for a property called 'fb-modes' in the QEMU,VGA node of
OpenBIOS.
If it is found all the resolutions are parsed and loaded.
Example command-line:
-prom-env resolutions=512x342,640x480,800x600,1024x600,1200x700,1440x900
Signed-off-by: John Arbuckle <address@hidden>
---
v5
Switched from using 'resolutions' to 'fb-modes' in the QEMU,VGA node
as Mark requested.
v4
Removed all ASCII text processing code and replaced it with integer
processing code.
v3
Changed implementation of atoi().
Removed strlen() implementation.
Removed pow() implementation.
Changed entry_id from pointer to automatic variable.
v2
Implemented my own malloc(), strlen(), pow(), and atoi() functions.
Removed free() calls.
Changed get_set_count() to get_resolution_set_count().
QemuVGADriver/src/QemuVga.c | 107 ++++++++++++++++++++++++++++++++++
+++++++++-
1 file changed, 105 insertions(+), 2 deletions(-)
diff --git a/QemuVGADriver/src/QemuVga.c b/QemuVGADriver/src/QemuVga.c
index 4584242..28daa02 100644
--- a/QemuVGADriver/src/QemuVga.c
+++ b/QemuVGADriver/src/QemuVga.c
@@ -18,9 +18,25 @@ static struct vMode vModes[] = {
{ 1600, 1200 },
{ 1920, 1080 },
{ 1920, 1200 },
- { 0,0 }
+ { 0,0 },
+ { 0,0 },
+ { 0,0 },
+ { 0,0 },
+ { 0,0 },
+ { 0,0 },
+ { 0,0 },
+ { 0,0 },
+ { 0,0 },
+ { 0,0 },
+ { 0,0 },
+ { 0,0 },
+ { 0,0 },
};
+/* The number of width-height pairs in the above vModes structure */
+#define AVAILABLE_SLOTS 20
+
+
static void VgaWriteB(UInt16 port, UInt8 val)
{
UInt8 *ptr;
@@ -148,11 +164,98 @@ static InterruptMemberNumber PCIInterruptHandler
(InterruptSetMember ISTmember,
#endif
+/* Returns the number of resolutions in the vModes array */
+static int get_number_of_resolutions()
+{
+ int size_of_array, num_of_resolutions, index;
+
+ num_of_resolutions = 0;
+ size_of_array = sizeof(vModes) / sizeof(struct vMode);
+
+ for(index = 0; index < size_of_array; index++)
+ {
+ if (vModes[index].width != 0) {
+ num_of_resolutions++;
+ }
+ }
+
+ return num_of_resolutions;
+}
+
+
+/* Looks in the /options node for the value of the resolutions
property */
+static int add_user_resolutions(void)
+{
+ RegEntryID entry_id;
+ OSErr err;
+ OSStatus os_status = noErr;
+ Boolean is_done;
+ void *value;
+ RegPropertyValueSize property_size = -1;
+ int index, res_set_count, *res_values;
+
+ #define PROPERTY_NAME "fb-modes"
+ #define NODE_PATH "Devices:device-tree:pci:QEMU,VGA"
+
+ /* init the entry variable */
+ err = RegistryEntryIDInit(&entry_id);
+ if (err != noErr) {
+ lprintf("Error: Failed to init entry variable! (Error: %d)\n",
err);
+ return err;
+ }
+ is_done = false;
+
+ /* Get the entry ID value */
+ err = RegistryCStrEntryLookup(NULL /* start root */, NODE_PATH,
&entry_id);
+ if (err != noErr) {
+ lprintf("RegistryCStrEntryLookup() failure (Error: %d)\n", err);
+ return err;
+ }
+
+ /* Get the size of the property */
+ os_status = RegistryPropertyGetSize(&entry_id, PROPERTY_NAME,
&property_size);
+ if (os_status != noErr) {
+ lprintf("Error: Failed to get property size! (Error: %d)\n",
os_status);
+ return os_status;
+ }
+
+ /* Allocate memory to the value variable */
+ value = (void *) PoolAllocateResident(property_size, false);
+ if (value == NULL) {
+ lprintf("Error: Failed to allocate memory to value variable\n");
+ return -1;
+ }
+
+ /* Get the value of the property */
+ err = RegistryPropertyGet(&entry_id, PROPERTY_NAME, value,
&property_size);
+ if (err != noErr) {
+ lprintf("Error: Failed to find property value %s! (Error: %d)\n",
PROPERTY_NAME, err);
+ return err;
+ }
+
+ res_values = value;
+ res_set_count = property_size/4/2; /* divide by bytes per cell then
by cells per set */
+
+ /* Limit the number of resolutions to number of available slots in
vMode */
+ res_set_count = (res_set_count > AVAILABLE_SLOTS ?
AVAILABLE_SLOTS : res_set_count);
+
+ /* Load each resolution set */
+ for(index = 0; index < res_set_count; index++)
+ {
+ vModes[index].width = *(res_values++);
+ vModes[index].height = *(res_values++);
+ }
+ return 0;
+}
+
+
OSStatus QemuVga_Init(void)
{
UInt16 id, i;
UInt32 mem, width, height, depth;
+ add_user_resolutions();
+
lprintf("First MMIO read...\n");
id = DispiReadW(VBE_DISPI_INDEX_ID);
mem = DispiReadW(VBE_DISPI_INDEX_VIDEO_MEMORY_64K);
@@ -183,7 +286,7 @@ OSStatus QemuVga_Init(void)
i = 0;
}
GLOBAL.bootMode = i;
- GLOBAL.numModes = sizeof(vModes) / sizeof(struct vMode) - 1;
+ GLOBAL.numModes = get_number_of_resolutions();
QemuVga_SetMode(GLOBAL.bootMode, depth, 0);
--
2.6.0
[Prev in Thread] |
Current Thread |
[Next in Thread] |
- [Qemu-ppc] [PATCH v5] Add resolutions via the command-line,
G 3 <=