10 Commits

Author SHA1 Message Date
Lauri Kenttä 62cc4a8cb7 Update change log and tag v2.6.0 2026-04-02 22:37:51 +03:00
Lauri Kenttä 630adfc50b Update shim to 16.1 (x64, aa64)
Use OL10 shim.
For ia32 we're stuck with shim 15.8, distros don't support it anymore.
2026-04-02 22:36:48 +03:00
Lauri Kenttä a78b6b22a3 Only install the weirdly named loader if shim 15 is used 2026-04-02 22:32:34 +03:00
Lauri Kenttä 7db9c2d3ec Suggest booting to FW to enable HackBGRT 2026-04-02 22:32:34 +03:00
Lauri Kenttä 28129c23fb Rename setup.log to setup-log.txt for easier use 2026-04-02 22:32:34 +03:00
Lauri Kenttä bc2a192506 Improve README for TPM, Secure Boot, only one HDD 2026-04-02 22:32:34 +03:00
Lauri Kenttä 3d5efa2117 Fix GetVariable with >4kB data 2026-04-02 22:32:34 +03:00
Lauri Kenttä 683ee49110 Allow position as a fraction of resolution
UEFI recommends y=.382 (1 - 1 / (golden ratio)), make this the default.
Fractional position starts with a decimal point: x=.5 y=.382
Pixel offset relative to the center is set as before: x=123 y=456
If the coordinates were omitted, old default was: x=0 y=0
2026-03-30 19:14:31 +03:00
Lauri Kenttä d40ce9f6c5 Make batch example the same as option I 2025-07-29 11:24:47 +03:00
Lauri Kenttä 447ff30f61 Fix getting last line from BCDEdit output 2025-07-29 11:14:37 +03:00
13 changed files with 204 additions and 81 deletions
+1 -1
View File
@@ -18,4 +18,4 @@ Explain exactly the steps you did:
4. ...
**Log file**
Run the setup again and select menu option `L` (or add parameter `show-boot-log` on command line). Attach the `setup.log` to this report.
Run the setup again and select menu option `L` (or add parameter `show-boot-log` on command line). Attach the `setup-log.txt` to this report.
+9
View File
@@ -2,6 +2,15 @@
All notable changes to this project will be documented in this file.
## 2.6.0 - 2026-04-02
### Added
- Allow setting image position as a fraction of resolution.
### Changed
- Update *shim* to 16.1 for x86_64 and Aarch64.
- Rename `setup.log` to `setup-log.txt` for easier use.
## 2.5.2 - 2025-04-13
### Fixed
+20 -9
View File
@@ -12,19 +12,30 @@ When booting on a UEFI-based computer, Windows may show a vendor-defined logo wh
**Important:** If you mess up the installation, your system may become unbootable! Create a rescue disk before use. This software comes with no warranty. Use at your own risk.
* Make sure that your computer is booting with UEFI.
* Make sure that you have read the Secure Boot instructions.
* Make sure that BitLocker is disabled, or find your recovery key.
### Secure Boot instructions
### Secure Boot
HackBGRT is not approved by Microsoft. Instead, HackBGRT comes with the *shim* boot loader, which allows to manually select HackBGRT as a trusted program. After installing HackBGRT and rebooting your computer, you have to **follow the instructions in [shim.md](shim.md)** to achieve this. These steps cannot be automated, that's the whole point of Secure Boot. Although HackBGRT is self-signed with a certificate, it's not advisable to enroll foreign certificates directly into your firmware.
The *shim* boot loader is maintained by Red Hat, Inc, and the included signed copy of *shim* is extracted from Debian GNU/Linux many thanks to the maintainers! For copyright information, see [shim-signed/COPYRIGHT](shim-signed/COPYRIGHT).
The *shim* boot loader is maintained by Red Hat, Inc, and the included signed copies of *shim* are extracted from various Linux distributions many thanks to the maintainers! For copyright information, see [shim-signed/COPYRIGHT](shim-signed/COPYRIGHT).
### TPM
TPM, or Trusted Platform Module, watches how your computer boots. When there is a change in the boot process such as using HackBGRT some things may stop working. This includes:
* BitLocker or similar disk encryption.
* Anti-cheat software.
* Windows PIN unlock method.
* Other security-related things which mention TPM.
You should disable these features before using HackBGRT. Some of them can be re-enabled afterwards, some can't. For any TPM problems, it's recommended to either uninstall HackBGRT or stop using the problematic feature.
(If you find an easy way to reconfigure the TPM, please document, test and share it. Technically one solution would be to install HackBGRT before Windows and make sure that Windows is always booted through HackBGRT. But that's easier said than done.)
### Windows installation
* Make sure you **read the above sections**.
* Get the latest release from the Releases page.
* Make sure you have only one bootable hard drive. Otherwise the automatic setup may fail.
* Start `setup.exe` and follow the instructions.
* The installer will launch Paint for editing the image, or you can edit it otherwise.
* For advanced settings, edit `config.txt` before installing. No extra support provided!
@@ -55,7 +66,7 @@ The *shim* boot loader is maintained by Red Hat, Inc, and the included signed co
* `arch=...` force architecture.
* `esp=...` force EFI System Partition path.
* `dry-run` skip actual changes.
* For example, run `setup.exe batch install allow-secure-boot enable-overwrite` to copy files and overwrite the MS boot loader regardless of Secure Boot status.
* For example, `setup.exe batch disable install enable-bcdedit` would disable any previous installation, then install the files and create the EFI boot entry with `bcdedit`.
### Multi-boot configurations
@@ -75,7 +86,7 @@ HackBGRT tries to read its configuration from the same directory where it's inst
## Configuration
The configuration options are described in `config.txt`, which the installer copies into `[EFI System Partition]\EFI\HackBGRT\config.txt`.
The configuration options are described in `config.txt`, which the installer copies into `[EFI System Partition]\EFI\HackBGRT\config.txt`. For debugging purposes, the same options may be given also as command line parameters in the EFI Shell.
## Images
@@ -130,7 +141,7 @@ If the default logo works, try again with your custom image. Make sure that the
When you get your image working with the default configuration, you can do any other necessary changes to `config.txt`.
If the default logo does not work, check the boot log again to see if there is some obvious error.
You may report an issue and attach the `setup.log` file.
You may report an issue and attach the `setup-log.txt` file.
### Impossible to boot at all
+10 -9
View File
@@ -1,5 +1,5 @@
# vim: set fileencoding=utf-8
# The same options may be given also as command line parameters in the EFI Shell, which is useful for debugging.
# Lines starting with '#' are comments.
# Boot loader path. MS = either backup or original Windows boot loader.
boot=MS
@@ -8,12 +8,13 @@ boot=MS
# Multiple image lines may be present, in which case one will be picked by random.
# The image line may contain the following parts:
# Any of the following:
# - "n=(number)", a weight for this image in the randomization process. Default: n=1.
# - "x=(number)" or "x=keep", the x offset from the center. Default: x=0.
# - "y=(number)" or "y=keep", the y offset from the center. Default: y=0.
# - "o=(0|90|180|270|keep)", the screen orientation, degrees anticlockwise. Default: o=keep.
# - "x=(number) y=(number)" positions the image relative to the screen center.
# - "x=.(decimal) y=.(decimal)" positions the image as a fraction of the resolution.
# - "o=(0|90|180|270|keep)", the screen orientation, degrees anticlockwise.
# - "n=(number)", a weight for this image in the randomization process.
# - Default values: o=keep x=.5 y=.382 n=1
# One of the following:
# - "keep" to keep the firmware logo. Also keeps coordinates by default.
# - "keep" to keep the firmware logo (and coordinates, unless specified).
# - "remove" to remove the BGRT. Makes x and y meaningless.
# - "black" to use only a black image. Makes x and y meaningless.
# - "path=file.bmp" to read an image file.
@@ -21,9 +22,9 @@ boot=MS
# Examples:
# - image=remove
# - image=black
# - image= x=0 y=-200 path=topimage.bmp
# - image= x=0 y=.0 path=topimage.bmp
# - image= n=1 o=90 path=sideways.bmp
# - image= n=50 y=999999 o=keep path=probable.bmp
# - image= n=50 y=999999 path=probable.bmp
# The above examples together would produce
# - 1/54 chance for the default OS logo
# - 1/54 chance for black screen
@@ -31,7 +32,7 @@ boot=MS
# - 1/54 chance for splash.bmp, centered, orientation set to 90 degrees
# - 50/54 chance for probable.bmp, at the bottom edge, explicitly default orientation
# Default: just one image.
image= y=-200 path=splash.bmp
image= path=splash.bmp
# Preferred resolution. Use 0x0 for maximum and -1x-1 for original.
resolution=0x0
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
+5 -1
View File
@@ -35,6 +35,9 @@ public class Efi {
[DllImport("kernel32.dll", SetLastError = true)]
private static extern UInt32 GetSystemFirmwareTable(UInt32 provider, UInt32 table, [MarshalAs(UnmanagedType.LPArray)] byte[] buffer, UInt32 len);
[DllImport("kernel32.dll", SetLastError = true)]
private static extern void SetLastError(UInt32 errorCode);
[StructLayout(LayoutKind.Sequential, Pack = 1)]
private struct TokPriv1Luid {
public int Count;
@@ -144,6 +147,7 @@ public class Efi {
for (UInt32 i = 4096; i <= 1024*1024; i *= 2) {
byte[] buf = new byte[i];
SetLastError(0);
UInt32 len = GetFirmwareEnvironmentVariableEx(name, guid, buf, (UInt32) buf.Length, out result.Attributes);
if (len == buf.Length) {
continue;
@@ -159,7 +163,7 @@ public class Efi {
return result;
}
const int ERROR_INVALID_FUNCTION = 0x1;
var msg = $"GetVariable: error 0x{error:X08}: ${new Win32Exception(error).Message}";
var msg = $"GetVariable: error 0x{error:X08}: {new Win32Exception(error).Message}";
throw error == ERROR_INVALID_FUNCTION ? new NotImplementedException(msg) : new Exception(msg);
}
throw new Exception("GetVariable: result exceeds 1MB");
+33 -6
View File
@@ -71,6 +71,7 @@ public class Setup {
"disable",
"uninstall",
"boot-to-fw",
"ask-to-boot-to-fw",
"show-boot-log",
};
@@ -142,7 +143,7 @@ public class Setup {
var timestamp = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss.fff");
var pid = System.Diagnostics.Process.GetCurrentProcess().Id;
var prefix = $"{timestamp} | pid {pid} | ";
File.AppendAllText("setup.log", prefix + s.Replace("\n", "\n" + prefix) + "\n");
File.AppendAllText("setup-log.txt", prefix + s.Replace("\n", "\n" + prefix) + "\n");
}
/**
@@ -420,7 +421,11 @@ public class Setup {
if (!SkipShim) {
InstallFile(shimSource, loaderDest);
InstallFile(mmSource, $"mm{EfiArch}.efi");
InstallFile(loaderSource, "\u4957\u444e\u574f\u0053\u0058"); // bytes "WINDOWS\0X\0" as UTF-16
var shimContents = File.ReadAllBytes(shimSource);
var shimContentsStr = System.Text.Encoding.ASCII.GetString(shimContents);
if (shimContentsStr.IndexOf("Version: 15.") >= 0) {
InstallFile(loaderSource, "\u4957\u444e\u574f\u0053\u0058"); // bytes "WINDOWS\0X\0" as UTF-16
}
loaderDest = $"grub{EfiArch}.efi";
}
InstallFile(loaderSource, loaderDest);
@@ -457,7 +462,7 @@ public class Setup {
if (bcdeditEnum.ExitCode != 0) {
if (bcdeditEnum.Output != null) {
var lines = bcdeditEnum.Output.Split("\n".ToCharArray());
var lastLine = lines.Select(s => s != "").Last();
var lastLine = lines.Where(s => s != "").Last();
WriteLine($"BCDEdit failed with: {lastLine}");
}
WriteLine("BCDEdit failed. See README for further information.");
@@ -813,6 +818,26 @@ public class Setup {
}
}
/**
* Ask if the user wants to boot to the UEFI setup.
*/
protected void AskToBootToFW() {
WriteLine();
WriteLine("Sometimes HackBGRT needs to be enabled manually in the UEFI setup.");
WriteLine("You can do that now, or later if you notice that HackBGRT isn't working.");
WriteLine("Find 'Boot options' or something similar and move HackBGRT before Windows.");
if (!Efi.CanBootToFW()) {
return;
}
WriteLine("Do you want to reboot and enter the UEFI setup now? (Y/N)");
var k = Console.ReadKey().Key;
Log($"User input: {k}");
WriteLine();
if (k == ConsoleKey.Y) {
BootToFW();
}
}
/**
* Detect the EFI architecture.
*/
@@ -935,9 +960,9 @@ public class Setup {
Configure();
}
if (k == ConsoleKey.I) {
RunPrivilegedActions(new string[] { "disable", "install", "enable-bcdedit" });
RunPrivilegedActions(new string[] { "disable", "install", "enable-bcdedit", "ask-to-boot-to-fw" });
} else if (k == ConsoleKey.J) {
RunPrivilegedActions(new string[] { "disable", "install", "enable-entry" });
RunPrivilegedActions(new string[] { "disable", "install", "enable-entry", "ask-to-boot-to-fw" });
} else if (k == ConsoleKey.O) {
RunPrivilegedActions(new string[] { "disable", "install", "enable-overwrite" });
} else if (k == ConsoleKey.F) {
@@ -1050,6 +1075,8 @@ public class Setup {
Disable();
} else if (arg == "uninstall") {
Uninstall();
} else if (arg == "ask-to-boot-to-fw") {
AskToBootToFW();
} else if (arg == "boot-to-fw") {
BootToFW();
} else if (arg == "show-boot-log") {
@@ -1137,7 +1164,7 @@ public class Setup {
WriteLine("This was a dry run, your system was not actually modified.");
}
if (!Batch) {
WriteLine("If you need to report a bug,\n - run this setup again with menu option L (show-boot-log)\n - then include the setup.log file with your report.");
WriteLine("If you need to report a bug,\n - run this setup again with menu option L (show-boot-log)\n - then include the setup-log.txt file with your report.");
WriteLine("Press any key to quit.");
Console.ReadKey();
}
+64 -29
View File
@@ -68,54 +68,89 @@ BOOLEAN ReadConfigFile(struct HackBGRT_config* config, EFI_FILE_HANDLE base_dir,
return TRUE;
}
static void SetBMPWithRandom(struct HackBGRT_config* config, int weight, enum HackBGRT_action action, int x, int y, int o, const CHAR16* path) {
static void SetBMPWithRandom(struct HackBGRT_config* config, const struct HackBGRT_image_config* image, int weight) {
config->image_weight_sum += weight;
UINT32 random = (((UINT64) Random() & 0xffffffff) * config->image_weight_sum) >> 32;
UINT32 limit = ((UINT64) 0xffffffff * weight) >> 32;
Log(config->debug, L"%s n=%d, action=%d, x=%d, y=%d, o=%d, path=%s, rand=%x/%x\n", random <= limit ? L"Using" : L"Skipping", weight, action, x, y, o, path, random, limit);
Log(
config->debug,
L"image n=%d, action=%d, x=%d (mode %d), y=%d (mode %d), o=%d, path=%s, rand=%x/%x, chosen=%d\n",
weight, image->action, image->x, image->x_mode, image->y, image->y_mode, image->orientation, image->path, random, limit, (random <= limit)
);
if (random <= limit) {
config->action = action;
config->image_path = path;
config->orientation = o;
config->image_x = x;
config->image_y = y;
config->image = *image;
}
}
static int ParseCoordinate(const CHAR16* str, enum HackBGRT_action action) {
if (str && ((L'0' <= str[0] && str[0] <= L'9') || str[0] == L'-')) {
return str[0] == L'-' ? -(int)Atoi(str+1) : (int)Atoi(str);
static void ParseCoordinate(const CHAR16* str, int* out_int, enum HackBGRT_coordinate_mode* out_mode) {
if (!str) {
return;
}
if ((str && StrnCmp(str, L"keep", 4) == 0) || action == HackBGRT_KEEP) {
return HackBGRT_coord_keep;
if (StrnCmp(str, L"keep", 4) == 0) {
*out_int = 0;
*out_mode = HackBGRT_COORDINATE_MODE_KEEP;
return;
}
if (str[0] == L'.' && L'0' <= str[1] && str[1] <= L'9') {
int result = 0, i = 1, length = 0;
for (length = 0; length < HackBGRT_FRACTION_DIGITS; ++length) {
result = 10 * result;
if (L'0' <= str[i] && str[i] <= L'9') {
result += str[i] - L'0';
i += 1;
}
}
*out_mode = HackBGRT_COORDINATE_MODE_FRACTION;
*out_int = result;
return;
}
int neg = str[0] == L'-' ? 1 : 0;
if (L'0' <= str[neg] && str[neg] <= L'9') {
*out_int = Atoi(str + neg) * (neg ? -1 : 1);
*out_mode = HackBGRT_COORDINATE_MODE_CENTERED;
return;
}
return 0;
}
static void ReadConfigImage(struct HackBGRT_config* config, const CHAR16* line) {
const CHAR16* n = StrStrAfter(line, L"n=");
const CHAR16* x = StrStrAfter(line, L"x=");
const CHAR16* y = StrStrAfter(line, L"y=");
const CHAR16* o = StrStrAfter(line, L"o=");
const CHAR16* f = StrStrAfter(line, L"path=");
enum HackBGRT_action action = HackBGRT_KEEP;
if (f) {
action = HackBGRT_REPLACE;
struct HackBGRT_image_config image = {
.action = HackBGRT_ACTION_KEEP,
.orientation = HackBGRT_ORIENTATION_KEEP,
};
const CHAR16* tmp;
image.path = StrStrAfter(line, L"path=");
if (image.path) {
image.action = HackBGRT_ACTION_REPLACE;
// Default: x centered, y 38.2 % (= 1 - 1 / golden_ratio)
image.x_mode = image.y_mode = HackBGRT_COORDINATE_MODE_FRACTION;
image.x = HackBGRT_FRACTION_HALF;
image.y = HackBGRT_FRACTION_381966011;
} else if (StrStr(line, L"remove")) {
action = HackBGRT_REMOVE;
image.action = HackBGRT_ACTION_REMOVE;
} else if (StrStr(line, L"black")) {
action = HackBGRT_REPLACE;
image.action = HackBGRT_ACTION_REPLACE;
image.path = 0;
} else if (StrStr(line, L"keep")) {
action = HackBGRT_KEEP;
image.action = HackBGRT_ACTION_KEEP;
image.x_mode = image.y_mode = HackBGRT_COORDINATE_MODE_KEEP;
} else {
Log(1, L"Invalid image line: %s\n", line);
return;
}
int weight = n && (!f || n < f) ? Atoi(n) : 1;
int x_val = ParseCoordinate(x, action);
int y_val = ParseCoordinate(y, action);
int o_val = o ? ParseCoordinate(o, action) : HackBGRT_coord_keep;
SetBMPWithRandom(config, weight, action, x_val, y_val, o_val, f);
ParseCoordinate(StrStrAfter(line, L"x="), &image.x, &image.x_mode);
ParseCoordinate(StrStrAfter(line, L"y="), &image.y, &image.y_mode);
if (StrStrAfter(line, L"o=keep")) {
image.orientation = HackBGRT_ORIENTATION_KEEP;
} else if ((tmp = StrStrAfter(line, L"o="))) {
// convert orientation in degrees to number 0-3 (* 90 degrees)
int i = tmp[0] == L'-' ? -(int)Atoi(tmp+1) : (int)Atoi(tmp);
image.orientation = (i / 90) & 3;
}
int weight = 1;
if ((tmp = StrStrAfter(line, L"n="))) {
weight = Atoi(tmp);
}
SetBMPWithRandom(config, &image, weight);
}
static void ReadConfigResolution(struct HackBGRT_config* config, const CHAR16* line) {
+36 -8
View File
@@ -6,15 +6,47 @@
* Possible actions to perform on the BGRT.
*/
enum HackBGRT_action {
HackBGRT_KEEP = 0, HackBGRT_REPLACE, HackBGRT_REMOVE
HackBGRT_ACTION_KEEP = 0,
HackBGRT_ACTION_REPLACE,
HackBGRT_ACTION_REMOVE
};
/**
* Special values for the image coordinates.
* @see struct HackBGRT_config
*/
enum HackBGRT_coordinate {
HackBGRT_coord_keep = -1000001
enum HackBGRT_coordinate_mode {
HackBGRT_COORDINATE_MODE_KEEP = 0,
HackBGRT_COORDINATE_MODE_CENTERED,
HackBGRT_COORDINATE_MODE_FRACTION,
};
/**
* Constants for the fractional coordinates.
*/
enum HackBGRT_fraction {
HackBGRT_FRACTION_DIGITS = 4,
HackBGRT_FRACTION_ONE = 10000,
HackBGRT_FRACTION_HALF = 5000,
HackBGRT_FRACTION_381966011 = 3820,
};
/**
* Possible values for the orientation.
*/
enum HackBGRT_orientation {
HackBGRT_ORIENTATION_KEEP = -1,
};
/**
* The configuration for one image.
*/
struct HackBGRT_image_config {
enum HackBGRT_action action;
const CHAR16* path;
enum HackBGRT_coordinate_mode x_mode, y_mode;
int x, y;
int orientation;
};
/**
@@ -22,12 +54,8 @@ enum HackBGRT_coordinate {
*/
struct HackBGRT_config {
int debug, log;
enum HackBGRT_action action;
const CHAR16* image_path;
int image_x;
int image_y;
struct HackBGRT_image_config image;
int image_weight_sum;
int orientation;
int resolution_x;
int resolution_y;
int old_resolution_x;
+26 -18
View File
@@ -21,7 +21,6 @@ EFI_RUNTIME_SERVICES *RT;
*/
static struct HackBGRT_config config = {
.log = 1,
.action = HackBGRT_KEEP,
};
/**
@@ -163,13 +162,13 @@ static ACPI_BGRT* HandleAcpiTables(enum HackBGRT_action action, ACPI_BGRT* bgrt)
}
Log(config.debug, L" - ACPI table @%x: %s, revision = %d, OEM ID = %s\n", (UINTN)entry, TmpStr(entry->signature, 4), entry->revision, TmpStr(entry->oem_id, 6));
switch (action) {
case HackBGRT_KEEP:
case HackBGRT_ACTION_KEEP:
if (!bgrt) {
Log(config.debug, L" -> Returning this one for later use.\n");
bgrt = (ACPI_BGRT*) entry;
}
break;
case HackBGRT_REMOVE:
case HackBGRT_ACTION_REMOVE:
Log(config.debug, L" -> Deleting.\n");
for (int k = j+1; k < entry_arr_length; ++k) {
entry_arr[k-1] = entry_arr[k];
@@ -179,13 +178,13 @@ static ACPI_BGRT* HandleAcpiTables(enum HackBGRT_action action, ACPI_BGRT* bgrt)
xsdt->length -= sizeof(entry_arr[0]);
--j;
break;
case HackBGRT_REPLACE:
case HackBGRT_ACTION_REPLACE:
Log(config.debug, L" -> Replacing.\n");
entry_arr[j] = (UINTN) bgrt;
}
bgrt_count += 1;
}
if (!bgrt_count && action == HackBGRT_REPLACE && bgrt) {
if (!bgrt_count && action == HackBGRT_ACTION_REPLACE && bgrt) {
Log(config.debug, L" - Adding missing BGRT.\n");
xsdt = CreateXsdt(xsdt, entry_arr_length + 1);
entry_arr = (UINT64*)&xsdt[1];
@@ -303,13 +302,13 @@ static void CropBMP(BMP* bmp, int w, int h) {
*/
void HackBgrt(EFI_FILE_HANDLE base_dir) {
// REMOVE: simply delete all BGRT entries.
if (config.action == HackBGRT_REMOVE) {
HandleAcpiTables(config.action, 0);
if (config.image.action == HackBGRT_ACTION_REMOVE) {
HandleAcpiTables(config.image.action, 0);
return;
}
// KEEP/REPLACE: first get the old BGRT entry.
ACPI_BGRT* bgrt = HandleAcpiTables(HackBGRT_KEEP, 0);
ACPI_BGRT* bgrt = HandleAcpiTables(HackBGRT_ACTION_KEEP, 0);
// Get the old BMP and position (relative to screen center), if possible.
const int old_valid = bgrt && VerifyAcpiSdtChecksum(bgrt);
@@ -324,7 +323,7 @@ void HackBgrt(EFI_FILE_HANDLE base_dir) {
// Missing BGRT?
if (!bgrt) {
// Keep missing = do nothing.
if (config.action == HackBGRT_KEEP) {
if (config.image.action == HackBGRT_ACTION_KEEP) {
return;
}
// Replace missing = allocate new.
@@ -351,13 +350,13 @@ void HackBgrt(EFI_FILE_HANDLE base_dir) {
// Get the image (either old or new).
BMP* new_bmp = old_bmp;
if (config.action == HackBGRT_REPLACE) {
new_bmp = LoadBMP(base_dir, config.image_path);
if (config.image.action == HackBGRT_ACTION_REPLACE) {
new_bmp = LoadBMP(base_dir, config.image.path);
}
// No image = no need for BGRT.
if (!new_bmp) {
HandleAcpiTables(HackBGRT_REMOVE, 0);
HandleAcpiTables(HackBGRT_ACTION_REMOVE, 0);
return;
}
@@ -366,16 +365,23 @@ void HackBgrt(EFI_FILE_HANDLE base_dir) {
// Set the image address and orientation.
bgrt->image_address = (UINTN) new_bmp;
const int new_orientation = config.orientation == HackBGRT_coord_keep ? old_orientation : ((config.orientation / 90) & 3);
const int new_orientation = config.image.orientation == HackBGRT_ORIENTATION_KEEP ? old_orientation : config.image.orientation;
bgrt->status = new_orientation << 1;
// New center coordinates.
const int new_x = config.image_x == HackBGRT_coord_keep ? old_x : config.image_x;
const int new_y = config.image_y == HackBGRT_coord_keep ? old_y : config.image_y;
const int new_swap = new_orientation & 1;
const int new_reso_x = new_swap ? config.resolution_y : config.resolution_x;
const int new_reso_y = new_swap ? config.resolution_x : config.resolution_y;
const int new_x =
config.image.x_mode == HackBGRT_COORDINATE_MODE_KEEP ? old_x :
config.image.x_mode == HackBGRT_COORDINATE_MODE_CENTERED ? config.image.x :
(config.image.x - HackBGRT_FRACTION_HALF) * new_reso_x / HackBGRT_FRACTION_ONE;
const int new_y =
config.image.y_mode == HackBGRT_COORDINATE_MODE_KEEP ? old_y :
config.image.y_mode == HackBGRT_COORDINATE_MODE_CENTERED ? config.image.y :
(config.image.y - HackBGRT_FRACTION_HALF) * new_reso_y / HackBGRT_FRACTION_ONE;
// Calculate absolute position.
const int max_x = new_reso_x - new_bmp->width;
const int max_y = new_reso_y - new_bmp->height;
@@ -383,15 +389,17 @@ void HackBgrt(EFI_FILE_HANDLE base_dir) {
bgrt->image_offset_y = max(0, min(max_y, new_y + (new_reso_y - new_bmp->height) / 2));
Log(config.debug,
L"BMP at (%d, %d), center (%d, %d), resolution (%d, %d), orientation %d.\n",
L"Screen %dx%d, BMP %dx%d, center (%d, %d) = corner (%d, %d), orientation %d.\n",
new_reso_x, new_reso_y,
new_bmp->width, new_bmp->height,
new_x, new_y,
(int) bgrt->image_offset_x, (int) bgrt->image_offset_y,
new_x, new_y, new_reso_x, new_reso_y,
new_orientation * 90
);
// Store this BGRT in the ACPI tables.
SetAcpiSdtChecksum(bgrt);
HandleAcpiTables(HackBGRT_REPLACE, bgrt);
HandleAcpiTables(HackBGRT_ACTION_REPLACE, bgrt);
}
/**