Skip to content
GitLab
Menu
Projects
Groups
Snippets
Loading...
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
Menu
Open sidebar
dadigang
Ventoy
Commits
a5c70651
Commit
a5c70651
authored
Jun 15, 2020
by
longpanda
Browse files
1.0.13 release
parent
785255b6
Changes
55
Hide whitespace changes
Inline
Side-by-side
Showing
20 changed files
with
2846 additions
and
861 deletions
+2846
-861
DOC/BuildVentoyFromSource.txt
DOC/BuildVentoyFromSource.txt
+3
-1
EDK2/edk2_mod/edk2-edk2-stable201911/MdeModulePkg/Application/Ventoy/Ventoy.c
...dk2-stable201911/MdeModulePkg/Application/Ventoy/Ventoy.c
+105
-664
EDK2/edk2_mod/edk2-edk2-stable201911/MdeModulePkg/Application/Ventoy/Ventoy.h
...dk2-stable201911/MdeModulePkg/Application/Ventoy/Ventoy.h
+33
-3
EDK2/edk2_mod/edk2-edk2-stable201911/MdeModulePkg/Application/Ventoy/Ventoy.inf
...2-stable201911/MdeModulePkg/Application/Ventoy/Ventoy.inf
+1
-0
EDK2/edk2_mod/edk2-edk2-stable201911/MdeModulePkg/Application/Ventoy/VentoyProtocol.c
...le201911/MdeModulePkg/Application/Ventoy/VentoyProtocol.c
+631
-0
GRUB2/MOD_SRC/grub-2.04/grub-core/commands/test.c
GRUB2/MOD_SRC/grub-2.04/grub-core/commands/test.c
+491
-0
GRUB2/MOD_SRC/grub-2.04/grub-core/fs/fshelp.c
GRUB2/MOD_SRC/grub-2.04/grub-core/fs/fshelp.c
+7
-0
GRUB2/MOD_SRC/grub-2.04/grub-core/fs/iso9660.c
GRUB2/MOD_SRC/grub-2.04/grub-core/fs/iso9660.c
+10
-2
GRUB2/MOD_SRC/grub-2.04/grub-core/kern/disk.c
GRUB2/MOD_SRC/grub-2.04/grub-core/kern/disk.c
+1
-1
GRUB2/MOD_SRC/grub-2.04/grub-core/kern/file.c
GRUB2/MOD_SRC/grub-2.04/grub-core/kern/file.c
+23
-0
GRUB2/MOD_SRC/grub-2.04/grub-core/kern/main.c
GRUB2/MOD_SRC/grub-2.04/grub-core/kern/main.c
+45
-0
GRUB2/MOD_SRC/grub-2.04/grub-core/normal/menu.c
GRUB2/MOD_SRC/grub-2.04/grub-core/normal/menu.c
+39
-24
GRUB2/MOD_SRC/grub-2.04/grub-core/ventoy/ventoy.c
GRUB2/MOD_SRC/grub-2.04/grub-core/ventoy/ventoy.c
+120
-4
GRUB2/MOD_SRC/grub-2.04/grub-core/ventoy/ventoy_def.h
GRUB2/MOD_SRC/grub-2.04/grub-core/ventoy/ventoy_def.h
+36
-1
GRUB2/MOD_SRC/grub-2.04/grub-core/ventoy/ventoy_json.c
GRUB2/MOD_SRC/grub-2.04/grub-core/ventoy/ventoy_json.c
+5
-0
GRUB2/MOD_SRC/grub-2.04/grub-core/ventoy/ventoy_linux.c
GRUB2/MOD_SRC/grub-2.04/grub-core/ventoy/ventoy_linux.c
+45
-0
GRUB2/MOD_SRC/grub-2.04/grub-core/ventoy/ventoy_plugin.c
GRUB2/MOD_SRC/grub-2.04/grub-core/ventoy/ventoy_plugin.c
+451
-4
GRUB2/MOD_SRC/grub-2.04/grub-core/ventoy/ventoy_windows.c
GRUB2/MOD_SRC/grub-2.04/grub-core/ventoy/ventoy_windows.c
+554
-157
GRUB2/MOD_SRC/grub-2.04/include/grub/file.h
GRUB2/MOD_SRC/grub-2.04/include/grub/file.h
+243
-0
GRUB2/MOD_SRC/grub-2.04/include/grub/ventoy.h
GRUB2/MOD_SRC/grub-2.04/include/grub/ventoy.h
+3
-0
No files found.
DOC/BuildVentoyFromSource.txt
View file @
a5c70651
...
...
@@ -199,5 +199,7 @@
INSTALL/EFI/BOOT/MokManager.efi --> EFI/BOOT/MokManager.efi SHA-256: 3bf1f46cee0832355c7dd1dba880dea9bcaa78cc44375a1559d43bc9db18933b
5.11 INSTALL/tool/ash
https://busybox.net/downloads/binaries/1.31.0-i686-uclibc/ busybox_ASH
SHA-256: 2943f02f85fee0c9551aec47110a558a73f919c032b3c51e56d6f197b5ec4d7b
EDK2/edk2_mod/edk2-edk2-stable201911/MdeModulePkg/Application/Ventoy/Ventoy.c
View file @
a5c70651
...
...
@@ -36,34 +36,24 @@
#include <Protocol/SimpleFileSystem.h>
#include <Ventoy.h>
UINTN
g_iso_buf_size
=
0
;
BOOLEAN
gMemdiskMode
=
FALSE
;
BOOLEAN
gDebugPrint
=
FALSE
;
BOOLEAN
gLoadIsoEfi
=
FALSE
;
ventoy_ram_disk
g_ramdisk_param
;
ventoy_chain_head
*
g_chain
;
ventoy_img_chunk
*
g_chunk
;
UINT8
*
g_os_param_reserved
;
UINT32
g_img_chunk_num
;
ventoy_override_chunk
*
g_override_chunk
;
UINT32
g_override_chunk_num
;
ventoy_virt_chunk
*
g_virt_chunk
;
UINT32
g_virt_chunk_num
;
vtoy_block_data
gBlockData
;
ventoy_sector_flag
*
g_sector_flag
=
NULL
;
UINT32
g_sector_flag_num
=
0
;
static
grub_env_get_pf
grub_env_get
=
NULL
;
EFI_FILE_OPEN
g_original_fopen
=
NULL
;
EFI_FILE_CLOSE
g_original_fclose
=
NULL
;
EFI_SIMPLE_FILE_SYSTEM_PROTOCOL_OPEN_VOLUME
g_original_open_volume
=
NULL
;
ventoy_grub_param_file_replace
*
g_file_replace_list
=
NULL
;
ventoy_efi_file_replace
g_efi_file_replace
;
CHAR16
gFirstTryBootFile
[
256
]
=
{
0
};
CONST
CHAR16
gIso9660EfiDriverPath
[]
=
ISO9660_EFI_DRIVER_PATH
;
/* Boot filename */
UINTN
gBootFileStartIndex
=
1
;
CONST
CHAR16
*
gEfiBootFileName
[]
=
...
...
@@ -76,9 +66,6 @@ CONST CHAR16 *gEfiBootFileName[] =
L"
\\
efi
\\
boot
\\
bootx64.efi"
,
};
/* EFI block device vendor device path GUID */
EFI_GUID
gVtoyBlockDevicePathGuid
=
VTOY_BLOCK_DEVICE_PATH_GUID
;
VOID
EFIAPI
VtoyDebug
(
IN
CONST
CHAR8
*
Format
,
...)
{
VA_LIST
Marker
;
...
...
@@ -204,6 +191,12 @@ static void EFIAPI ventoy_dump_chain(ventoy_chain_head *chain)
debug
(
"os_param->vtoy_img_size=<%llu>"
,
chain
->
os_param
.
vtoy_img_size
);
debug
(
"os_param->vtoy_img_location_addr=<0x%llx>"
,
chain
->
os_param
.
vtoy_img_location_addr
);
debug
(
"os_param->vtoy_img_location_len=<%u>"
,
chain
->
os_param
.
vtoy_img_location_len
);
debug
(
"os_param->vtoy_reserved=<%u %u %u %u>"
,
g_os_param_reserved
[
0
],
g_os_param_reserved
[
1
],
g_os_param_reserved
[
2
],
g_os_param_reserved
[
3
]
);
ventoy_debug_pause
();
...
...
@@ -224,312 +217,102 @@ static void EFIAPI ventoy_dump_chain(ventoy_chain_head *chain)
ventoy_dump_virt_chunk
(
chain
);
}
EFI_HANDLE
EFIAPI
ventoy_get_parent_handle
(
IN
EFI_DEVICE_PATH_PROTOCOL
*
pDevPath
)
static
int
ventoy_update_image_location
(
ventoy_os_param
*
param
)
{
EFI_HANDLE
Handle
=
NULL
;
EFI_STATUS
Status
=
EFI_SUCCESS
;
EFI_DEVICE_PATH_PROTOCOL
*
pLastNode
=
NULL
;
EFI_DEVICE_PATH_PROTOCOL
*
pCurNode
=
NULL
;
EFI_DEVICE_PATH_PROTOCOL
*
pTmpDevPath
=
NULL
;
pTmpDevPath
=
DuplicateDevicePath
(
pDevPath
);
if
(
!
pTmpDevPath
)
{
return
NULL
;
}
UINT8
chksum
=
0
;
unsigned
int
i
;
unsigned
int
length
;
UINTN
address
=
0
;
void
*
buffer
=
NULL
;
ventoy_image_location
*
location
=
NULL
;
ventoy_image_disk_region
*
region
=
NULL
;
ventoy_img_chunk
*
chunk
=
g_chunk
;
pCurNode
=
pTmpDevPath
;
while
(
!
IsDevicePathEnd
(
pCurNode
))
{
pLastNode
=
pCurNode
;
pCurNode
=
NextDevicePathNode
(
pCurNode
);
}
if
(
pLastNode
)
length
=
sizeof
(
ventoy_image_location
)
+
(
g_img_chunk_num
-
1
)
*
sizeof
(
ventoy_image_disk_region
);
Status
=
gBS
->
AllocatePool
(
EfiRuntimeServicesData
,
length
+
4096
*
2
,
&
buffer
);
if
(
EFI_ERROR
(
Status
)
||
NULL
==
buffer
)
{
CopyMem
(
pLastNode
,
pCurNode
,
sizeof
(
EFI_DEVICE_PATH_PROTOCOL
));
debug
(
"Failed to allocate runtime pool %r
\n
"
,
Status
);
return
1
;
}
pCurNode
=
pTmpDevPath
;
Status
=
gBS
->
LocateDevicePath
(
&
gEfiDevicePathProtocolGuid
,
&
pCurNode
,
&
Handle
);
debug
(
"Status:%r Parent Handle:%p DP:%s"
,
Status
,
Handle
,
ConvertDevicePathToText
(
pTmpDevPath
,
FALSE
,
FALSE
));
FreePool
(
pTmpDevPath
);
return
Handle
;
}
EFI_STATUS
EFIAPI
ventoy_block_io_reset
(
IN
EFI_BLOCK_IO_PROTOCOL
*
This
,
IN
BOOLEAN
ExtendedVerification
)
{
(
VOID
)
This
;
(
VOID
)
ExtendedVerification
;
return
EFI_SUCCESS
;
}
address
=
(
UINTN
)
buffer
;
STATIC
EFI_STATUS
EFIAPI
ventoy_read_iso_sector
(
IN
UINT64
Sector
,
IN
UINTN
Count
,
OUT
VOID
*
Buffer
)
{
EFI_STATUS
Status
=
EFI_SUCCESS
;
EFI_LBA
MapLba
=
0
;
UINT32
i
=
0
;
UINTN
secLeft
=
0
;
UINTN
secRead
=
0
;
UINT64
ReadStart
=
0
;
UINT64
ReadEnd
=
0
;
UINT64
OverrideStart
=
0
;
UINT64
OverrideEnd
=
0
;
UINT8
*
pCurBuf
=
(
UINT8
*
)
Buffer
;
ventoy_img_chunk
*
pchunk
=
g_chunk
;
ventoy_override_chunk
*
pOverride
=
g_override_chunk
;
EFI_BLOCK_IO_PROTOCOL
*
pRawBlockIo
=
gBlockData
.
pRawBlockIo
;
debug
(
"read iso sector %lu count %u"
,
Sector
,
Count
);
ReadStart
=
Sector
*
2048
;
ReadEnd
=
(
Sector
+
Count
)
*
2048
;
for
(
i
=
0
;
Count
>
0
&&
i
<
g_img_chunk_num
;
i
++
,
pchunk
++
)
if
(
address
%
4096
)
{
if
(
Sector
>=
pchunk
->
img_start_sector
&&
Sector
<=
pchunk
->
img_end_sector
)
{
if
(
g_chain
->
disk_sector_size
==
512
)
{
MapLba
=
(
Sector
-
pchunk
->
img_start_sector
)
*
4
+
pchunk
->
disk_start_sector
;
}
else
{
MapLba
=
(
Sector
-
pchunk
->
img_start_sector
)
*
2048
/
g_chain
->
disk_sector_size
+
pchunk
->
disk_start_sector
;
}
secLeft
=
pchunk
->
img_end_sector
+
1
-
Sector
;
secRead
=
(
Count
<
secLeft
)
?
Count
:
secLeft
;
Status
=
pRawBlockIo
->
ReadBlocks
(
pRawBlockIo
,
pRawBlockIo
->
Media
->
MediaId
,
MapLba
,
secRead
*
2048
,
pCurBuf
);
if
(
EFI_ERROR
(
Status
))
{
debug
(
"Raw disk read block failed %r"
,
Status
);
return
Status
;
}
Count
-=
secRead
;
Sector
+=
secRead
;
pCurBuf
+=
secRead
*
2048
;
}
address
+=
4096
-
(
address
%
4096
);
}
if
(
ReadStart
>
g_chain
->
real_img_size_in_bytes
)
param
->
chksum
=
0
;
param
->
vtoy_img_location_addr
=
address
;
param
->
vtoy_img_location_len
=
length
;
/* update check sum */
for
(
i
=
0
;
i
<
sizeof
(
ventoy_os_param
);
i
++
)
{
return
EFI_SUCCESS
;
chksum
+=
*
((
UINT8
*
)
param
+
i
)
;
}
param
->
chksum
=
(
chksum
==
0
)
?
0
:
(
UINT8
)(
0x100
-
chksum
);
/* override data */
pCurBuf
=
(
UINT8
*
)
Buffer
;
for
(
i
=
0
;
i
<
g_override_chunk_num
;
i
++
,
pOverride
++
)
location
=
(
ventoy_image_location
*
)(
unsigned
long
)(
param
->
vtoy_img_location_addr
);
if
(
NULL
==
location
)
{
OverrideStart
=
pOverride
->
img_offset
;
OverrideEnd
=
pOverride
->
img_offset
+
pOverride
->
override_size
;
if
(
OverrideStart
>=
ReadEnd
||
ReadStart
>=
OverrideEnd
)
{
continue
;
}
if
(
ReadStart
<=
OverrideStart
)
{
if
(
ReadEnd
<=
OverrideEnd
)
{
CopyMem
(
pCurBuf
+
OverrideStart
-
ReadStart
,
pOverride
->
override_data
,
ReadEnd
-
OverrideStart
);
}
else
{
CopyMem
(
pCurBuf
+
OverrideStart
-
ReadStart
,
pOverride
->
override_data
,
pOverride
->
override_size
);
}
}
else
{
if
(
ReadEnd
<=
OverrideEnd
)
{
CopyMem
(
pCurBuf
,
pOverride
->
override_data
+
ReadStart
-
OverrideStart
,
ReadEnd
-
ReadStart
);
}
else
{
CopyMem
(
pCurBuf
,
pOverride
->
override_data
+
ReadStart
-
OverrideStart
,
OverrideEnd
-
ReadStart
);
}
}
return
0
;
}
return
EFI_SUCCESS
;
}
EFI_STATUS
EFIAPI
ventoy_block_io_ramdisk_read
(
IN
EFI_BLOCK_IO_PROTOCOL
*
This
,
IN
UINT32
MediaId
,
IN
EFI_LBA
Lba
,
IN
UINTN
BufferSize
,
OUT
VOID
*
Buffer
)
{
//debug("### ventoy_block_io_ramdisk_read sector:%u count:%u", (UINT32)Lba, (UINT32)BufferSize / 2048);
CopyMem
(
&
location
->
guid
,
&
param
->
guid
,
sizeof
(
ventoy_guid
));
location
->
image_sector_size
=
2048
;
location
->
disk_sector_size
=
g_chain
->
disk_sector_size
;
location
->
region_count
=
g_img_chunk_num
;
(
VOID
)
This
;
(
VOID
)
MediaId
;
region
=
location
->
regions
;
CopyMem
(
Buffer
,
(
char
*
)
g_chain
+
(
Lba
*
2048
),
BufferSize
);
for
(
i
=
0
;
i
<
g_img_chunk_num
;
i
++
)
{
region
->
image_sector_count
=
chunk
->
img_end_sector
-
chunk
->
img_start_sector
+
1
;
region
->
image_start_sector
=
chunk
->
img_start_sector
;
region
->
disk_start_sector
=
chunk
->
disk_start_sector
;
region
++
;
chunk
++
;
}
return
EFI_SUCCESS
;
return
0
;
}
EFI_STATUS
EFIAPI
ventoy_block_io_read
(
IN
EFI_BLOCK_IO_PROTOCOL
*
This
,
IN
UINT32
MediaId
,
IN
EFI_LBA
Lba
,
IN
UINTN
BufferSize
,
OUT
VOID
*
Buffer
)
EFI_HANDLE
EFIAPI
ventoy_get_parent_handle
(
IN
EFI_DEVICE_PATH_PROTOCOL
*
pDevPath
)
{
UINT32
i
=
0
;
UINT32
j
=
0
;
UINT32
lbacount
=
0
;
UINT32
secNum
=
0
;
UINT64
offset
=
0
;
EFI_LBA
curlba
=
0
;
EFI_LBA
lastlba
=
0
;
UINT8
*
lastbuffer
;
ventoy_sector_flag
*
cur_flag
;
ventoy_virt_chunk
*
node
;
EFI_HANDLE
Handle
=
NULL
;
EFI_STATUS
Status
=
EFI_SUCCESS
;
EFI_DEVICE_PATH_PROTOCOL
*
pLastNode
=
NULL
;
EFI_DEVICE_PATH_PROTOCOL
*
pCurNode
=
NULL
;
EFI_DEVICE_PATH_PROTOCOL
*
pTmpDevPath
=
NULL
;
//debug("### ventoy_block_io_read sector:%u count:%u", (UINT32)Lba, (UINT32)BufferSize / 2048);
secNum
=
BufferSize
/
2048
;
offset
=
Lba
*
2048
;
if
(
offset
+
BufferSize
<=
g_chain
->
real_img_size_in_bytes
)
{
return
ventoy_read_iso_sector
(
Lba
,
secNum
,
Buffer
);
}
if
(
secNum
>
g_sector_flag_num
)
{
cur_flag
=
AllocatePool
(
secNum
*
sizeof
(
ventoy_sector_flag
));
if
(
NULL
==
cur_flag
)
{
return
EFI_OUT_OF_RESOURCES
;
}
FreePool
(
g_sector_flag
);
g_sector_flag
=
cur_flag
;
g_sector_flag_num
=
secNum
;
}
for
(
curlba
=
Lba
,
cur_flag
=
g_sector_flag
,
j
=
0
;
j
<
secNum
;
j
++
,
curlba
++
,
cur_flag
++
)
pTmpDevPath
=
DuplicateDevicePath
(
pDevPath
);
if
(
!
pTmpDevPath
)
{
cur_flag
->
flag
=
0
;
for
(
node
=
g_virt_chunk
,
i
=
0
;
i
<
g_virt_chunk_num
;
i
++
,
node
++
)
{
if
(
curlba
>=
node
->
mem_sector_start
&&
curlba
<
node
->
mem_sector_end
)
{
CopyMem
((
UINT8
*
)
Buffer
+
j
*
2048
,
(
char
*
)
g_virt_chunk
+
node
->
mem_sector_offset
+
(
curlba
-
node
->
mem_sector_start
)
*
2048
,
2048
);
cur_flag
->
flag
=
1
;
break
;
}
else
if
(
curlba
>=
node
->
remap_sector_start
&&
curlba
<
node
->
remap_sector_end
)
{
cur_flag
->
remap_lba
=
node
->
org_sector_start
+
curlba
-
node
->
remap_sector_start
;
cur_flag
->
flag
=
2
;
break
;
}
}
return
NULL
;
}
for
(
curlba
=
Lba
,
cur_flag
=
g_sector_flag
,
j
=
0
;
j
<
secNum
;
j
++
,
curlba
++
,
cur_flag
++
)
pCurNode
=
pTmpDevPath
;
while
(
!
IsDevicePathEnd
(
pCurNode
))
{
if
(
cur_flag
->
flag
==
2
)
{
if
(
lastlba
==
0
)
{
lastbuffer
=
(
UINT8
*
)
Buffer
+
j
*
2048
;
lastlba
=
cur_flag
->
remap_lba
;
lbacount
=
1
;
}
else
if
(
lastlba
+
lbacount
==
cur_flag
->
remap_lba
)
{
lbacount
++
;
}
else
{
ventoy_read_iso_sector
(
lastlba
,
lbacount
,
lastbuffer
);
lastbuffer
=
(
UINT8
*
)
Buffer
+
j
*
2048
;
lastlba
=
cur_flag
->
remap_lba
;
lbacount
=
1
;
}
}
pLastNode
=
pCurNode
;
pCurNode
=
NextDevicePathNode
(
pCurNode
);
}
if
(
lbacount
>
0
)
if
(
pLastNode
)
{
ventoy_read_iso_sector
(
lastlba
,
lbacount
,
lastbuffer
);
CopyMem
(
pLastNode
,
pCurNode
,
sizeof
(
EFI_DEVICE_PATH_PROTOCOL
)
);
}
return
EFI_SUCCESS
;
}
EFI_STATUS
EFIAPI
ventoy_block_io_write
(
IN
EFI_BLOCK_IO_PROTOCOL
*
This
,
IN
UINT32
MediaId
,
IN
EFI_LBA
Lba
,
IN
UINTN
BufferSize
,
IN
VOID
*
Buffer
)
{
(
VOID
)
This
;
(
VOID
)
MediaId
;
(
VOID
)
Lba
;
(
VOID
)
BufferSize
;
(
VOID
)
Buffer
;
return
EFI_WRITE_PROTECTED
;
}
EFI_STATUS
EFIAPI
ventoy_block_io_flush
(
IN
EFI_BLOCK_IO_PROTOCOL
*
This
)
{
(
VOID
)
This
;
return
EFI_SUCCESS
;
}
EFI_STATUS
EFIAPI
ventoy_fill_device_path
(
VOID
)
{
UINTN
NameLen
=
0
;
UINT8
TmpBuf
[
128
]
=
{
0
};
VENDOR_DEVICE_PATH
*
venPath
=
NULL
;
venPath
=
(
VENDOR_DEVICE_PATH
*
)
TmpBuf
;
NameLen
=
StrSize
(
VTOY_BLOCK_DEVICE_PATH_NAME
);
venPath
->
Header
.
Type
=
HARDWARE_DEVICE_PATH
;
venPath
->
Header
.
SubType
=
HW_VENDOR_DP
;
venPath
->
Header
.
Length
[
0
]
=
sizeof
(
VENDOR_DEVICE_PATH
)
+
NameLen
;
venPath
->
Header
.
Length
[
1
]
=
0
;
CopyMem
(
&
venPath
->
Guid
,
&
gVtoyBlockDevicePathGuid
,
sizeof
(
EFI_GUID
));
CopyMem
(
venPath
+
1
,
VTOY_BLOCK_DEVICE_PATH_NAME
,
NameLen
);
gBlockData
.
Path
=
AppendDevicePathNode
(
NULL
,
(
EFI_DEVICE_PATH_PROTOCOL
*
)
TmpBuf
);
gBlockData
.
DevicePathCompareLen
=
sizeof
(
VENDOR_DEVICE_PATH
)
+
NameLen
;
pCurNode
=
pTmpDevPath
;
Status
=
gBS
->
LocateDevicePath
(
&
gEfiDevicePathProtocolGuid
,
&
pCurNode
,
&
Handle
);
debug
(
"Status:%r Parent Handle:%p DP:%s"
,
Status
,
Handle
,
ConvertDevicePathToText
(
pTmpDevPath
,
FALSE
,
FALSE
));
debug
(
"gBlockData.Path=<%s>
\n
"
,
ConvertDevicePathToText
(
gBlockData
.
Path
,
FALSE
,
FALSE
)
);
FreePool
(
pTmpDevPath
);
return
EFI_SUCCESS
;
return
Handle
;
}
EFI_STATUS
EFIAPI
ventoy_save_ramdisk_param
(
VOID
)
...
...
@@ -545,7 +328,7 @@ EFI_STATUS EFIAPI ventoy_save_ramdisk_param(VOID)
return
Status
;
}
EFI_STATUS
EFIAPI
ventoy_del_ramdisk_param
(
VOID
)
EFI_STATUS
EFIAPI
ventoy_del
ete
_ramdisk_param
(
VOID
)
{
EFI_STATUS
Status
=
EFI_SUCCESS
;
EFI_GUID
VarGuid
=
VENTOY_GUID
;
...
...
@@ -559,7 +342,7 @@ EFI_STATUS EFIAPI ventoy_del_ramdisk_param(VOID)
}
EFI_STATUS
EFIAPI
ventoy_se
t
_variable
(
VOID
)
EFI_STATUS
EFIAPI
ventoy_s
av
e_variable
(
VOID
)
{
EFI_STATUS
Status
=
EFI_SUCCESS
;
EFI_GUID
VarGuid
=
VENTOY_GUID
;
...
...
@@ -585,56 +368,7 @@ EFI_STATUS EFIAPI ventoy_delete_variable(VOID)
return
Status
;
}
EFI_STATUS
EFIAPI
ventoy_install_blockio
(
IN
EFI_HANDLE
ImageHandle
,
IN
UINT64
ImgSize
)
{
EFI_STATUS
Status
=
EFI_SUCCESS
;
EFI_BLOCK_IO_PROTOCOL
*
pBlockIo
=
&
(
gBlockData
.
BlockIo
);
ventoy_fill_device_path
();
gBlockData
.
Media
.
BlockSize
=
2048
;
gBlockData
.
Media
.
LastBlock
=
ImgSize
/
2048
-
1
;
gBlockData
.
Media
.
ReadOnly
=
TRUE
;
gBlockData
.
Media
.
MediaPresent
=
1
;
gBlockData
.
Media
.
LogicalBlocksPerPhysicalBlock
=
1
;
pBlockIo
->
Revision
=
EFI_BLOCK_IO_PROTOCOL_REVISION3
;
pBlockIo
->
Media
=
&
(
gBlockData
.
Media
);
pBlockIo
->
Reset
=
ventoy_block_io_reset
;
if
(
gMemdiskMode
)
{
pBlockIo
->
ReadBlocks
=
ventoy_block_io_ramdisk_read
;
}
else
{
pBlockIo
->
ReadBlocks
=
ventoy_block_io_read
;
}
pBlockIo
->
WriteBlocks
=
ventoy_block_io_write
;
pBlockIo
->
FlushBlocks
=
ventoy_block_io_flush
;
Status
=
gBS
->
InstallMultipleProtocolInterfaces
(
&
gBlockData
.
Handle
,
&
gEfiBlockIoProtocolGuid
,
&
gBlockData
.
BlockIo
,
&
gEfiDevicePathProtocolGuid
,
gBlockData
.
Path
,
NULL
);
debug
(
"Install protocol %r"
,
Status
);
if
(
EFI_ERROR
(
Status
))
{
return
Status
;
}
Status
=
gBS
->
ConnectController
(
gBlockData
.
Handle
,
NULL
,
NULL
,
1
);
debug
(
"Connect controller %r"
,
Status
);
return
EFI_SUCCESS
;
}
EFI_STATUS
EFIAPI
ventoy_load_image
STATIC
EFI_STATUS
EFIAPI
ventoy_load_image
(
IN
EFI_HANDLE
ImageHandle
,
IN
EFI_DEVICE_PATH_PROTOCOL
*
pDevicePath
,
...
...
@@ -745,156 +479,6 @@ STATIC EFI_STATUS EFIAPI ventoy_find_iso_disk(IN EFI_HANDLE ImageHandle)
}
}
STATIC
EFI_STATUS
EFIAPI
ventoy_find_iso_disk_fs
(
IN
EFI_HANDLE
ImageHandle
)
{
UINTN
i
=
0
;
UINTN
Count
=
0
;
EFI_HANDLE
Parent
=
NULL
;
EFI_HANDLE
*
Handles
=
NULL
;
EFI_STATUS
Status
=
EFI_SUCCESS
;
EFI_SIMPLE_FILE_SYSTEM_PROTOCOL
*
pFile
=
NULL
;
EFI_DEVICE_PATH_PROTOCOL
*
pDevPath
=
NULL
;
Status
=
gBS
->
LocateHandleBuffer
(
ByProtocol
,
&
gEfiSimpleFileSystemProtocolGuid
,
NULL
,
&
Count
,
&
Handles
);
if
(
EFI_ERROR
(
Status
))
{
return
Status
;
}
debug
(
"ventoy_find_iso_disk_fs fs count:%u"
,
Count
);
for
(
i
=
0
;
i
<
Count
;
i
++
)
{
Status
=
gBS
->
HandleProtocol
(
Handles
[
i
],
&
gEfiSimpleFileSystemProtocolGuid
,
(
VOID
**
)
&
pFile
);
if
(
EFI_ERROR
(
Status
))
{
continue
;
}
Status
=
gBS
->
OpenProtocol
(
Handles
[
i
],
&
gEfiDevicePathProtocolGuid
,
(
VOID
**
)
&
pDevPath
,
ImageHandle
,
Handles
[
i
],
EFI_OPEN_PROTOCOL_GET_PROTOCOL
);
if
(
EFI_ERROR
(
Status
))
{
debug
(
"Failed to open device path protocol %r"
,
Status
);
continue
;
}
debug
(
"Handle:%p FS DP: <%s>"
,
Handles
[
i
],
ConvertDevicePathToText
(
pDevPath
,
FALSE
,
FALSE
));
Parent
=
ventoy_get_parent_handle
(
pDevPath
);
if
(
Parent
==
gBlockData
.
RawBlockIoHandle
)
{
debug
(
"Find ventoy disk fs"
);
gBlockData
.
DiskFsHandle
=
Handles
[
i
];
gBlockData
.
pDiskFs
=
pFile
;
gBlockData
.
pDiskFsDevPath
=
pDevPath
;
break
;
}
}
FreePool
(
Handles
);
return
EFI_SUCCESS
;
}
STATIC
EFI_STATUS
EFIAPI
ventoy_load_isoefi_driver
(
IN
EFI_HANDLE
ImageHandle
)
{
EFI_HANDLE
Image
=
NULL
;
EFI_STATUS
Status
=
EFI_SUCCESS
;
CHAR16
LogVar
[
4
]
=
L"5"
;
Status
=
ventoy_load_image
(
ImageHandle
,
gBlockData
.
pDiskFsDevPath
,
gIso9660EfiDriverPath
,
sizeof
(
gIso9660EfiDriverPath
),
&
Image
);
debug
(
"load iso efi driver status:%r"
,
Status
);
if
(
gDebugPrint
)
{
gRT
->
SetVariable
(
L"FS_LOGGING"
,
&
gShellVariableGuid
,
EFI_VARIABLE_BOOTSERVICE_ACCESS
|
EFI_VARIABLE_RUNTIME_ACCESS
,
sizeof
(
LogVar
),
LogVar
);
}
gRT
->
SetVariable
(
L"FS_NAME_NOCASE"
,
&
gShellVariableGuid
,
EFI_VARIABLE_BOOTSERVICE_ACCESS
|
EFI_VARIABLE_RUNTIME_ACCESS
,
sizeof
(
LogVar
),
LogVar
);
gBlockData
.
IsoDriverImage
=
Image
;
Status
=
gBS
->
StartImage
(
Image
,
NULL
,
NULL
);
debug
(
"Start iso efi driver status:%r"
,
Status
);
return
EFI_SUCCESS
;
}
static
int
ventoy_update_image_location
(
ventoy_os_param
*
param
)
{
EFI_STATUS
Status
=
EFI_SUCCESS
;
UINT8
chksum
=
0
;
unsigned
int
i
;
unsigned
int
length
;
UINTN
address
=
0
;
void
*
buffer
=
NULL
;
ventoy_image_location
*
location
=
NULL
;
ventoy_image_disk_region
*
region
=
NULL
;
ventoy_img_chunk
*
chunk
=
g_chunk
;
length
=
sizeof
(
ventoy_image_location
)
+
(
g_img_chunk_num
-
1
)
*
sizeof
(
ventoy_image_disk_region
);
Status
=
gBS
->
AllocatePool
(
EfiRuntimeServicesData
,
length
+
4096
*
2
,
&
buffer
);
if
(
EFI_ERROR
(
Status
)
||
NULL
==
buffer
)
{
debug
(
"Failed to allocate runtime pool %r
\n
"
,
Status
);
return
1
;
}
address
=
(
UINTN
)
buffer
;
if
(
address
%
4096
)
{
address
+=
4096
-
(
address
%
4096
);
}
param
->
chksum
=
0
;
param
->
vtoy_img_location_addr
=
address
;
param
->
vtoy_img_location_len
=
length
;
/* update check sum */
for
(
i
=
0
;
i
<
sizeof
(
ventoy_os_param
);
i
++
)
{
chksum
+=
*
((
UINT8
*
)
param
+
i
);
}
param
->
chksum
=
(
chksum
==
0
)
?
0
:
(
UINT8
)(
0x100
-
chksum
);
location
=
(
ventoy_image_location
*
)(
unsigned
long
)(
param
->
vtoy_img_location_addr
);
if
(
NULL
==
location
)
{
return
0
;
}
CopyMem
(
&
location
->
guid
,
&
param
->
guid
,
sizeof
(
ventoy_guid
));
location
->
image_sector_size
=
2048
;
location
->
disk_sector_size
=
g_chain
->
disk_sector_size
;
location
->
region_count
=
g_img_chunk_num
;
region
=
location
->
regions
;
for
(
i
=
0
;
i
<
g_img_chunk_num
;
i
++
)
{
region
->
image_sector_count
=
chunk
->
img_end_sector
-
chunk
->
img_start_sector
+
1
;
region
->
image_start_sector
=
chunk
->
img_start_sector
;
region
->
disk_start_sector
=
chunk
->
disk_start_sector
;
region
++
;
chunk
++
;
}
return
0
;
}
STATIC
EFI_STATUS
EFIAPI
ventoy_parse_cmdline
(
IN
EFI_HANDLE
ImageHandle
)
{
UINT32
i
=
0
;
...
...
@@ -923,11 +507,6 @@ STATIC EFI_STATUS EFIAPI ventoy_parse_cmdline(IN EFI_HANDLE ImageHandle)
gDebugPrint
=
TRUE
;
}
if
(
StrStr
(
pCmdLine
,
L"isoefi=on"
))
{
gLoadIsoEfi
=
TRUE
;
}
pPos
=
StrStr
(
pCmdLine
,
L"FirstTry=@"
);
if
(
pPos
)
{
...
...
@@ -998,6 +577,14 @@ STATIC EFI_STATUS EFIAPI ventoy_parse_cmdline(IN EFI_HANDLE ImageHandle)
g_virt_chunk
=
(
ventoy_virt_chunk
*
)((
char
*
)
g_chain
+
g_chain
->
virt_chunk_offset
);
g_virt_chunk_num
=
g_chain
->
virt_chunk_num
;
g_os_param_reserved
=
(
UINT8
*
)(
g_chain
->
os_param
.
vtoy_reserved
);
/* Workaround for Windows & ISO9660 */
if
(
g_os_param_reserved
[
2
]
==
1
&&
g_os_param_reserved
[
3
]
==
0
)
{
g_fixup_iso9660_secover_enable
=
TRUE
;
}
for
(
i
=
0
;
i
<
sizeof
(
ventoy_os_param
);
i
++
)
{
chksum
+=
*
((
UINT8
*
)(
&
(
g_chain
->
os_param
))
+
i
);
...
...
@@ -1020,82 +607,28 @@ STATIC EFI_STATUS EFIAPI ventoy_parse_cmdline(IN EFI_HANDLE ImageHandle)
return
EFI_SUCCESS
;
}
EFI_STATUS
EFIAPI
ventoy_wrapper_file_open
(
EFI_FILE_HANDLE
This
,
EFI_FILE_HANDLE
*
New
,
CHAR16
*
Name
,
UINT64
Mode
,
UINT64
Attributes
)
EFI_STATUS
EFIAPI
ventoy_clean_env
(
VOID
)
{
UINT32
i
=
0
;
UINT32
j
=
0
;
UINT64
Sectors
=
0
;
EFI_STATUS
Status
=
EFI_SUCCESS
;
CHAR8
TmpName
[
256
];
ventoy_virt_chunk
*
virt
=
NULL
;
Status
=
g_original_fopen
(
This
,
New
,
Name
,
Mode
,
Attributes
);
if
(
EFI_ERROR
(
Status
))
{
return
Status
;
}
if
(
g_file_replace_list
&&
g_file_replace_list
->
magic
==
GRUB_FILE_REPLACE_MAGIC
&&
g_file_replace_list
->
new_file_virtual_id
<
g_virt_chunk_num
)
{
AsciiSPrint
(
TmpName
,
sizeof
(
TmpName
),
"%s"
,
Name
);
for
(
j
=
0
;
j
<
4
;
j
++
)
{
if
(
0
==
AsciiStrCmp
(
g_file_replace_list
[
i
].
old_file_name
[
j
],
TmpName
))
{
g_original_fclose
(
*
New
);
*
New
=
&
g_efi_file_replace
.
WrapperHandle
;
ventoy_wrapper_file_procotol
(
*
New
);
virt
=
g_virt_chunk
+
g_file_replace_list
->
new_file_virtual_id
;
FreePool
(
g_sector_flag
);
g_sector_flag_num
=
0
;
Sectors
=
(
virt
->
mem_sector_end
-
virt
->
mem_sector_start
)
+
(
virt
->
remap_sector_end
-
virt
->
remap_sector_start
);
g_efi_file_replace
.
BlockIoSectorStart
=
virt
->
mem_sector_start
;
g_efi_file_replace
.
FileSizeBytes
=
Sectors
*
2048
;
gBS
->
DisconnectController
(
gBlockData
.
Handle
,
NULL
,
NULL
);
if
(
gDebugPrint
)
{
debug
(
"## ventoy_wrapper_file_open <%s> BlockStart:%lu Sectors:%lu Bytes:%lu"
,
Name
,
g_efi_file_replace
.
BlockIoSectorStart
,
Sectors
,
Sectors
*
2048
);
sleep
(
3
);
}
return
Status
;
}
}
}
gBS
->
UninstallMultipleProtocolInterfaces
(
gBlockData
.
Handle
,
&
gEfiBlockIoProtocolGuid
,
&
gBlockData
.
BlockIo
,
&
gEfiDevicePathProtocolGuid
,
gBlockData
.
Path
,
NULL
);
return
Status
;
}
ventoy_delete_variable
();
EFI_STATUS
EFIAPI
ventoy_wrapper_open_volume
(
IN
EFI_SIMPLE_FILE_SYSTEM_PROTOCOL
*
This
,
OUT
EFI_FILE_PROTOCOL
**
Root
)
{
EFI_STATUS
Status
=
EFI_SUCCESS
;
Status
=
g_original_open_volume
(
This
,
Root
);
if
(
!
EFI_ERROR
(
Status
))
if
(
g_chain
->
os_param
.
vtoy_img_location_addr
)
{
g_original_fopen
=
(
*
Root
)
->
Open
;
g_original_fclose
=
(
*
Root
)
->
Close
;
(
*
Root
)
->
Open
=
ventoy_wrapper_file_open
;
FreePool
((
VOID
*
)(
UINTN
)
g_chain
->
os_param
.
vtoy_img_location_addr
);
}
return
Status
;
return
EFI_SUCCESS
;
}
EFI_STATUS
EFIAPI
ventoy_boot
(
IN
EFI_HANDLE
ImageHandle
)
{
UINTN
t
=
0
;
...
...
@@ -1179,7 +712,7 @@ EFI_STATUS EFIAPI ventoy_boot(IN EFI_HANDLE ImageHandle)
if
(
g_file_replace_list
&&
g_file_replace_list
->
magic
==
GRUB_FILE_REPLACE_MAGIC
)
{
g_original
_open
_
volume
=
pFile
->
OpenVolume
;
ventoy_wrapper_push
_openvolume
(
pFile
->
OpenVolume
)
;
pFile
->
OpenVolume
=
ventoy_wrapper_open_volume
;
}
...
...
@@ -1210,74 +743,6 @@ EFI_STATUS EFIAPI ventoy_boot(IN EFI_HANDLE ImageHandle)
return
EFI_SUCCESS
;
}
EFI_STATUS
EFIAPI
ventoy_clean_env
(
VOID
)
{
FreePool
(
g_sector_flag
);
g_sector_flag_num
=
0
;
if
(
gLoadIsoEfi
&&
gBlockData
.
IsoDriverImage
)
{
gBS
->
UnloadImage
(
gBlockData
.
IsoDriverImage
);
}
gBS
->
DisconnectController
(
gBlockData
.
Handle
,
NULL
,
NULL
);
gBS
->
UninstallMultipleProtocolInterfaces
(
gBlockData
.
Handle
,
&
gEfiBlockIoProtocolGuid
,
&
gBlockData
.
BlockIo
,
&
gEfiDevicePathProtocolGuid
,
gBlockData
.
Path
,
NULL
);
ventoy_delete_variable
();
if
(
g_chain
->
os_param
.
vtoy_img_location_addr
)
{
FreePool
((
VOID
*
)(
UINTN
)
g_chain
->
os_param
.
vtoy_img_location_addr
);
}
return
EFI_SUCCESS
;
}
EFI_STATUS
EFIAPI
ventoy_ramdisk_boot
(
IN
EFI_HANDLE
ImageHandle
)
{
EFI_STATUS
Status
=
EFI_SUCCESS
;
EFI_RAM_DISK_PROTOCOL
*
RamDisk
=
NULL
;
EFI_DEVICE_PATH_PROTOCOL
*
DevicePath
=
NULL
;
debug
(
"RamDisk Boot ..."
);
Status
=
gBS
->
LocateProtocol
(
&
gEfiRamDiskProtocolGuid
,
NULL
,
(
VOID
**
)
&
RamDisk
);
if
(
EFI_ERROR
(
Status
))
{
debug
(
"Failed to locate ramdisk protocol %r"
,
Status
);
return
Status
;
}
debug
(
"Locate RamDisk Protocol %r ..."
,
Status
);
Status
=
RamDisk
->
Register
((
UINTN
)
g_chain
,
(
UINT64
)
g_iso_buf_size
,
&
gEfiVirtualCdGuid
,
NULL
,
&
DevicePath
);
if
(
EFI_ERROR
(
Status
))
{
debug
(
"Failed to register ramdisk %r"
,
Status
);
return
Status
;
}
debug
(
"Register RamDisk %r ..."
,
Status
);
debug
(
"RamDisk DevicePath:<%s> ..."
,
ConvertDevicePathToText
(
DevicePath
,
FALSE
,
FALSE
));
ventoy_debug_pause
();
gBlockData
.
Path
=
DevicePath
;
gBlockData
.
DevicePathCompareLen
=
GetDevicePathSize
(
DevicePath
)
-
sizeof
(
EFI_DEVICE_PATH_PROTOCOL
);
Status
=
ventoy_boot
(
ImageHandle
);
if
(
EFI_NOT_FOUND
==
Status
)
{
gST
->
ConOut
->
OutputString
(
gST
->
ConOut
,
L"No bootfile found for UEFI!
\r\n
"
);
gST
->
ConOut
->
OutputString
(
gST
->
ConOut
,
L"Maybe the image does not support "
VENTOY_UEFI_DESC
L"!
\r\n
"
);
sleep
(
300
);
}
return
EFI_SUCCESS
;
}
EFI_STATUS
EFIAPI
VentoyEfiMain
(
...
...
@@ -1309,26 +774,14 @@ EFI_STATUS EFIAPI VentoyEfiMain
ventoy_install_blockio
(
ImageHandle
,
g_iso_buf_size
);
Status
=
ventoy_boot
(
ImageHandle
);
if
(
EFI_NOT_FOUND
==
Status
)
{
gST
->
ConOut
->
OutputString
(
gST
->
ConOut
,
L"No bootfile found for UEFI!
\r\n
"
);
gST
->
ConOut
->
OutputString
(
gST
->
ConOut
,
L"Maybe the image does not support "
VENTOY_UEFI_DESC
L"!
\r\n
"
);
sleep
(
300
);
}
ventoy_del_ramdisk_param
();
ventoy_delete_ramdisk_param
();
}
else
{
ventoy_se
t
_variable
();
ventoy_s
av
e_variable
();
ventoy_find_iso_disk
(
ImageHandle
);
if
(
gLoadIsoEfi
)
{
ventoy_find_iso_disk_fs
(
ImageHandle
);
ventoy_load_isoefi_driver
(
ImageHandle
);
}
ventoy_debug_pause
();
ventoy_install_blockio
(
ImageHandle
,
g_chain
->
virt_img_size_in_bytes
);
...
...
@@ -1336,32 +789,20 @@ EFI_STATUS EFIAPI VentoyEfiMain
ventoy_debug_pause
();
Status
=
ventoy_boot
(
ImageHandle
);
if
(
EFI_NOT_FOUND
==
Status
)
{
if
(
!
gLoadIsoEfi
)
{
gLoadIsoEfi
=
TRUE
;
ventoy_find_iso_disk_fs
(
ImageHandle
);
ventoy_load_isoefi_driver
(
ImageHandle
);
Status
=
ventoy_boot
(
ImageHandle
);
}
if
(
EFI_NOT_FOUND
==
Status
)
{
gST
->
ConOut
->
OutputString
(
gST
->
ConOut
,
L"No bootfile found for UEFI!
\r\n
"
);
gST
->
ConOut
->
OutputString
(
gST
->
ConOut
,
L"Maybe the image does not support "
VENTOY_UEFI_DESC
L"!
\r\n
"
);
sleep
(
60
);
}
}
ventoy_clean_env
();
}
if
(
EFI_NOT_FOUND
==
Status
)
{
gST
->
ConOut
->
OutputString
(
gST
->
ConOut
,
L"No bootfile found for UEFI!
\r\n
"
);
gST
->
ConOut
->
OutputString
(
gST
->
ConOut
,
L"Maybe the image does not support "
VENTOY_UEFI_DESC
L"!
\r\n
"
);
sleep
(
30
);
}
ventoy_clear_input
();
gST
->
ConOut
->
ClearScreen
(
gST
->
ConOut
);
return
EFI_SUCCESS
;
}
EDK2/edk2_mod/edk2-edk2-stable201911/MdeModulePkg/Application/Ventoy/Ventoy.h
View file @
a5c70651
...
...
@@ -199,10 +199,8 @@ typedef struct vtoy_block_data
EFI_SIMPLE_FILE_SYSTEM_PROTOCOL
*
pDiskFs
;
EFI_DEVICE_PATH_PROTOCOL
*
pDiskFsDevPath
;
EFI_HANDLE
IsoDriverImage
;
}
vtoy_block_data
;
#define ISO9660_EFI_DRIVER_PATH L"\\ventoy\\iso9660_x64.efi"
#define debug(expr, ...) if (gDebugPrint) VtoyDebug("[VTOY] "expr"\r\n", ##__VA_ARGS__)
#define trace(expr, ...) VtoyDebug("[VTOY] "expr"\r\n", ##__VA_ARGS__)
...
...
@@ -254,6 +252,14 @@ typedef struct ventoy_ram_disk
UINT64
DiskSize
;
}
ventoy_ram_disk
;
typedef
struct
ventoy_iso9660_override
{
UINT32
first_sector
;
UINT32
first_sector_be
;
UINT32
size
;
UINT32
size_be
;
}
ventoy_iso9660_override
;
#pragma pack()
...
...
@@ -282,7 +288,6 @@ typedef struct ventoy_system_wrapper
bs->func = wrapper.New##func;\
}
extern
ventoy_efi_file_replace
g_efi_file_replace
;
extern
BOOLEAN
gDebugPrint
;
VOID
EFIAPI
VtoyDebug
(
IN
CONST
CHAR8
*
Format
,
...);
EFI_STATUS
EFIAPI
ventoy_wrapper_system
(
VOID
);
...
...
@@ -296,5 +301,30 @@ EFI_STATUS EFIAPI ventoy_block_io_read
OUT
VOID
*
Buffer
);
extern
ventoy_chain_head
*
g_chain
;
extern
ventoy_img_chunk
*
g_chunk
;
extern
UINT32
g_img_chunk_num
;
extern
ventoy_override_chunk
*
g_override_chunk
;
extern
UINT32
g_override_chunk_num
;
extern
ventoy_virt_chunk
*
g_virt_chunk
;
extern
UINT32
g_virt_chunk_num
;
extern
vtoy_block_data
gBlockData
;
extern
ventoy_efi_file_replace
g_efi_file_replace
;
extern
ventoy_sector_flag
*
g_sector_flag
;
extern
UINT32
g_sector_flag_num
;
extern
BOOLEAN
gMemdiskMode
;
extern
UINTN
g_iso_buf_size
;
extern
ventoy_grub_param_file_replace
*
g_file_replace_list
;
extern
BOOLEAN
g_fixup_iso9660_secover_enable
;
EFI_STATUS
EFIAPI
ventoy_wrapper_open_volume
(
IN
EFI_SIMPLE_FILE_SYSTEM_PROTOCOL
*
This
,
OUT
EFI_FILE_PROTOCOL
**
Root
);
EFI_STATUS
EFIAPI
ventoy_install_blockio
(
IN
EFI_HANDLE
ImageHandle
,
IN
UINT64
ImgSize
);
EFI_STATUS
EFIAPI
ventoy_wrapper_push_openvolume
(
IN
EFI_SIMPLE_FILE_SYSTEM_PROTOCOL_OPEN_VOLUME
OpenVolume
);
#endif
EDK2/edk2_mod/edk2-edk2-stable201911/MdeModulePkg/Application/Ventoy/Ventoy.inf
View file @
a5c70651
...
...
@@ -29,6 +29,7 @@
Ventoy.h
Ventoy.c
VentoyDebug.c
VentoyProtocol.c
[Packages]
MdePkg/MdePkg.dec
...
...
EDK2/edk2_mod/edk2-edk2-stable201911/MdeModulePkg/Application/Ventoy/VentoyProtocol.c
0 → 100644
View file @
a5c70651
/******************************************************************************
* Ventoy.c
*
* Copyright (c) 2020, longpanda <admin@ventoy.net>
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 3 of the
* License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, see <http://www.gnu.org/licenses/>.
*
*/
#include <Uefi.h>
#include <Library/DebugLib.h>
#include <Library/PrintLib.h>
#include <Library/UefiLib.h>
#include <Library/BaseMemoryLib.h>
#include <Library/DevicePathLib.h>
#include <Library/MemoryAllocationLib.h>
#include <Library/UefiBootServicesTableLib.h>
#include <Library/UefiRuntimeServicesTableLib.h>
#include <Library/UefiApplicationEntryPoint.h>
#include <Protocol/LoadedImage.h>
#include <Guid/FileInfo.h>
#include <Guid/FileSystemInfo.h>
#include <Protocol/BlockIo.h>
#include <Protocol/RamDisk.h>
#include <Protocol/SimpleFileSystem.h>
#include <Ventoy.h>
UINTN
g_iso_buf_size
=
0
;
BOOLEAN
gMemdiskMode
=
FALSE
;
ventoy_sector_flag
*
g_sector_flag
=
NULL
;
UINT32
g_sector_flag_num
=
0
;
EFI_FILE_OPEN
g_original_fopen
=
NULL
;
EFI_FILE_CLOSE
g_original_fclose
=
NULL
;
EFI_SIMPLE_FILE_SYSTEM_PROTOCOL_OPEN_VOLUME
g_original_open_volume
=
NULL
;
/* EFI block device vendor device path GUID */
EFI_GUID
gVtoyBlockDevicePathGuid
=
VTOY_BLOCK_DEVICE_PATH_GUID
;
#define VENTOY_ISO9660_SECTOR_OVERFLOW 2097152
BOOLEAN
g_fixup_iso9660_secover_enable
=
FALSE
;
BOOLEAN
g_fixup_iso9660_secover_start
=
FALSE
;
UINT64
g_fixup_iso9660_secover_1st_secs
=
0
;
UINT64
g_fixup_iso9660_secover_cur_secs
=
0
;
UINT64
g_fixup_iso9660_secover_tot_secs
=
0
;
EFI_STATUS
EFIAPI
ventoy_block_io_reset
(
IN
EFI_BLOCK_IO_PROTOCOL
*
This
,
IN
BOOLEAN
ExtendedVerification
)
{
(
VOID
)
This
;
(
VOID
)
ExtendedVerification
;
return
EFI_SUCCESS
;
}
STATIC
EFI_STATUS
EFIAPI
ventoy_read_iso_sector
(
IN
UINT64
Sector
,
IN
UINTN
Count
,
OUT
VOID
*
Buffer
)
{
EFI_STATUS
Status
=
EFI_SUCCESS
;
EFI_LBA
MapLba
=
0
;
UINT32
i
=
0
;
UINTN
secLeft
=
0
;
UINTN
secRead
=
0
;
UINT64
ReadStart
=
0
;
UINT64
ReadEnd
=
0
;
UINT64
OverrideStart
=
0
;
UINT64
OverrideEnd
=
0
;
UINT8
*
pCurBuf
=
(
UINT8
*
)
Buffer
;
ventoy_img_chunk
*
pchunk
=
g_chunk
;
ventoy_override_chunk
*
pOverride
=
g_override_chunk
;
EFI_BLOCK_IO_PROTOCOL
*
pRawBlockIo
=
gBlockData
.
pRawBlockIo
;
debug
(
"read iso sector %lu count %u"
,
Sector
,
Count
);
ReadStart
=
Sector
*
2048
;
ReadEnd
=
(
Sector
+
Count
)
*
2048
;
for
(
i
=
0
;
Count
>
0
&&
i
<
g_img_chunk_num
;
i
++
,
pchunk
++
)
{
if
(
Sector
>=
pchunk
->
img_start_sector
&&
Sector
<=
pchunk
->
img_end_sector
)
{
if
(
g_chain
->
disk_sector_size
==
512
)
{
MapLba
=
(
Sector
-
pchunk
->
img_start_sector
)
*
4
+
pchunk
->
disk_start_sector
;
}
else
{
MapLba
=
(
Sector
-
pchunk
->
img_start_sector
)
*
2048
/
g_chain
->
disk_sector_size
+
pchunk
->
disk_start_sector
;
}
secLeft
=
pchunk
->
img_end_sector
+
1
-
Sector
;
secRead
=
(
Count
<
secLeft
)
?
Count
:
secLeft
;
Status
=
pRawBlockIo
->
ReadBlocks
(
pRawBlockIo
,
pRawBlockIo
->
Media
->
MediaId
,
MapLba
,
secRead
*
2048
,
pCurBuf
);
if
(
EFI_ERROR
(
Status
))
{
debug
(
"Raw disk read block failed %r"
,
Status
);
return
Status
;
}
Count
-=
secRead
;
Sector
+=
secRead
;
pCurBuf
+=
secRead
*
2048
;
}
}
if
(
ReadStart
>
g_chain
->
real_img_size_in_bytes
)
{
return
EFI_SUCCESS
;
}
/* override data */
pCurBuf
=
(
UINT8
*
)
Buffer
;
for
(
i
=
0
;
i
<
g_override_chunk_num
;
i
++
,
pOverride
++
)
{
OverrideStart
=
pOverride
->
img_offset
;
OverrideEnd
=
pOverride
->
img_offset
+
pOverride
->
override_size
;
if
(
OverrideStart
>=
ReadEnd
||
ReadStart
>=
OverrideEnd
)
{
continue
;
}
if
(
ReadStart
<=
OverrideStart
)
{
if
(
ReadEnd
<=
OverrideEnd
)
{
CopyMem
(
pCurBuf
+
OverrideStart
-
ReadStart
,
pOverride
->
override_data
,
ReadEnd
-
OverrideStart
);
}
else
{
CopyMem
(
pCurBuf
+
OverrideStart
-
ReadStart
,
pOverride
->
override_data
,
pOverride
->
override_size
);
}
}
else
{
if
(
ReadEnd
<=
OverrideEnd
)
{
CopyMem
(
pCurBuf
,
pOverride
->
override_data
+
ReadStart
-
OverrideStart
,
ReadEnd
-
ReadStart
);
}
else
{
CopyMem
(
pCurBuf
,
pOverride
->
override_data
+
ReadStart
-
OverrideStart
,
OverrideEnd
-
ReadStart
);
}
}
if
(
g_fixup_iso9660_secover_enable
&&
(
!
g_fixup_iso9660_secover_start
)
&&
pOverride
->
override_size
==
sizeof
(
ventoy_iso9660_override
))
{
ventoy_iso9660_override
*
dirent
=
(
ventoy_iso9660_override
*
)
pOverride
->
override_data
;
if
(
dirent
->
first_sector
>=
VENTOY_ISO9660_SECTOR_OVERFLOW
)
{
g_fixup_iso9660_secover_start
=
TRUE
;
g_fixup_iso9660_secover_cur_secs
=
0
;
}
}
}
return
EFI_SUCCESS
;
}
EFI_STATUS
EFIAPI
ventoy_block_io_ramdisk_read
(
IN
EFI_BLOCK_IO_PROTOCOL
*
This
,
IN
UINT32
MediaId
,
IN
EFI_LBA
Lba
,
IN
UINTN
BufferSize
,
OUT
VOID
*
Buffer
)
{
//debug("### ventoy_block_io_ramdisk_read sector:%u count:%u", (UINT32)Lba, (UINT32)BufferSize / 2048);
(
VOID
)
This
;
(
VOID
)
MediaId
;
CopyMem
(
Buffer
,
(
char
*
)
g_chain
+
(
Lba
*
2048
),
BufferSize
);
return
EFI_SUCCESS
;
}
EFI_LBA
EFIAPI
ventoy_fixup_iso9660_sector
(
IN
EFI_LBA
Lba
,
UINT32
secNum
)
{
UINT32
i
=
0
;
if
(
g_fixup_iso9660_secover_cur_secs
>
0
)
{
Lba
+=
VENTOY_ISO9660_SECTOR_OVERFLOW
;
g_fixup_iso9660_secover_cur_secs
+=
secNum
;
if
(
g_fixup_iso9660_secover_cur_secs
>=
g_fixup_iso9660_secover_tot_secs
)
{
g_fixup_iso9660_secover_start
=
FALSE
;
goto
end
;
}
}
else
{
ventoy_iso9660_override
*
dirent
;
ventoy_override_chunk
*
pOverride
;
for
(
i
=
0
,
pOverride
=
g_override_chunk
;
i
<
g_override_chunk_num
;
i
++
,
pOverride
++
)
{
dirent
=
(
ventoy_iso9660_override
*
)
pOverride
->
override_data
;
if
(
Lba
==
dirent
->
first_sector
)
{
g_fixup_iso9660_secover_start
=
FALSE
;
goto
end
;
}
}
if
(
g_fixup_iso9660_secover_start
)
{
for
(
i
=
0
,
pOverride
=
g_override_chunk
;
i
<
g_override_chunk_num
;
i
++
,
pOverride
++
)
{
dirent
=
(
ventoy_iso9660_override
*
)
pOverride
->
override_data
;
if
(
Lba
+
VENTOY_ISO9660_SECTOR_OVERFLOW
==
dirent
->
first_sector
)
{
g_fixup_iso9660_secover_tot_secs
=
(
dirent
->
size
+
2047
)
/
2048
;
g_fixup_iso9660_secover_cur_secs
=
secNum
;
if
(
g_fixup_iso9660_secover_cur_secs
>=
g_fixup_iso9660_secover_tot_secs
)
{
g_fixup_iso9660_secover_start
=
FALSE
;
}
Lba
+=
VENTOY_ISO9660_SECTOR_OVERFLOW
;
goto
end
;
}
}
}
}
end:
return
Lba
;
}
EFI_STATUS
EFIAPI
ventoy_block_io_read
(
IN
EFI_BLOCK_IO_PROTOCOL
*
This
,
IN
UINT32
MediaId
,
IN
EFI_LBA
Lba
,
IN
UINTN
BufferSize
,
OUT
VOID
*
Buffer
)
{
UINT32
i
=
0
;
UINT32
j
=
0
;
UINT32
lbacount
=
0
;
UINT32
secNum
=
0
;
UINT64
offset
=
0
;
EFI_LBA
curlba
=
0
;
EFI_LBA
lastlba
=
0
;
UINT8
*
lastbuffer
;
ventoy_sector_flag
*
cur_flag
;
ventoy_virt_chunk
*
node
;
//debug("### ventoy_block_io_read sector:%u count:%u", (UINT32)Lba, (UINT32)BufferSize / 2048);
secNum
=
BufferSize
/
2048
;
/* Workaround for SSTR PE loader error */
if
(
g_fixup_iso9660_secover_start
)
{
Lba
=
ventoy_fixup_iso9660_sector
(
Lba
,
secNum
);
}
offset
=
Lba
*
2048
;
if
(
offset
+
BufferSize
<=
g_chain
->
real_img_size_in_bytes
)
{
return
ventoy_read_iso_sector
(
Lba
,
secNum
,
Buffer
);
}
if
(
secNum
>
g_sector_flag_num
)
{
cur_flag
=
AllocatePool
(
secNum
*
sizeof
(
ventoy_sector_flag
));
if
(
NULL
==
cur_flag
)
{
return
EFI_OUT_OF_RESOURCES
;
}
FreePool
(
g_sector_flag
);
g_sector_flag
=
cur_flag
;
g_sector_flag_num
=
secNum
;
}
for
(
curlba
=
Lba
,
cur_flag
=
g_sector_flag
,
j
=
0
;
j
<
secNum
;
j
++
,
curlba
++
,
cur_flag
++
)
{
cur_flag
->
flag
=
0
;
for
(
node
=
g_virt_chunk
,
i
=
0
;
i
<
g_virt_chunk_num
;
i
++
,
node
++
)
{
if
(
curlba
>=
node
->
mem_sector_start
&&
curlba
<
node
->
mem_sector_end
)
{
CopyMem
((
UINT8
*
)
Buffer
+
j
*
2048
,
(
char
*
)
g_virt_chunk
+
node
->
mem_sector_offset
+
(
curlba
-
node
->
mem_sector_start
)
*
2048
,
2048
);
cur_flag
->
flag
=
1
;
break
;
}
else
if
(
curlba
>=
node
->
remap_sector_start
&&
curlba
<
node
->
remap_sector_end
)
{
cur_flag
->
remap_lba
=
node
->
org_sector_start
+
curlba
-
node
->
remap_sector_start
;
cur_flag
->
flag
=
2
;
break
;
}
}
}
for
(
curlba
=
Lba
,
cur_flag
=
g_sector_flag
,
j
=
0
;
j
<
secNum
;
j
++
,
curlba
++
,
cur_flag
++
)
{
if
(
cur_flag
->
flag
==
2
)
{
if
(
lastlba
==
0
)
{
lastbuffer
=
(
UINT8
*
)
Buffer
+
j
*
2048
;
lastlba
=
cur_flag
->
remap_lba
;
lbacount
=
1
;
}
else
if
(
lastlba
+
lbacount
==
cur_flag
->
remap_lba
)
{
lbacount
++
;
}
else
{
ventoy_read_iso_sector
(
lastlba
,
lbacount
,
lastbuffer
);
lastbuffer
=
(
UINT8
*
)
Buffer
+
j
*
2048
;
lastlba
=
cur_flag
->
remap_lba
;
lbacount
=
1
;
}
}
}
if
(
lbacount
>
0
)
{
ventoy_read_iso_sector
(
lastlba
,
lbacount
,
lastbuffer
);
}
return
EFI_SUCCESS
;
}
EFI_STATUS
EFIAPI
ventoy_block_io_write
(
IN
EFI_BLOCK_IO_PROTOCOL
*
This
,
IN
UINT32
MediaId
,
IN
EFI_LBA
Lba
,
IN
UINTN
BufferSize
,
IN
VOID
*
Buffer
)
{
(
VOID
)
This
;
(
VOID
)
MediaId
;
(
VOID
)
Lba
;
(
VOID
)
BufferSize
;
(
VOID
)
Buffer
;
return
EFI_WRITE_PROTECTED
;
}
EFI_STATUS
EFIAPI
ventoy_block_io_flush
(
IN
EFI_BLOCK_IO_PROTOCOL
*
This
)
{
(
VOID
)
This
;
return
EFI_SUCCESS
;
}
EFI_STATUS
EFIAPI
ventoy_fill_device_path
(
VOID
)
{
UINTN
NameLen
=
0
;
UINT8
TmpBuf
[
128
]
=
{
0
};
VENDOR_DEVICE_PATH
*
venPath
=
NULL
;
venPath
=
(
VENDOR_DEVICE_PATH
*
)
TmpBuf
;
NameLen
=
StrSize
(
VTOY_BLOCK_DEVICE_PATH_NAME
);
venPath
->
Header
.
Type
=
HARDWARE_DEVICE_PATH
;
venPath
->
Header
.
SubType
=
HW_VENDOR_DP
;
venPath
->
Header
.
Length
[
0
]
=
sizeof
(
VENDOR_DEVICE_PATH
)
+
NameLen
;
venPath
->
Header
.
Length
[
1
]
=
0
;
CopyMem
(
&
venPath
->
Guid
,
&
gVtoyBlockDevicePathGuid
,
sizeof
(
EFI_GUID
));
CopyMem
(
venPath
+
1
,
VTOY_BLOCK_DEVICE_PATH_NAME
,
NameLen
);
gBlockData
.
Path
=
AppendDevicePathNode
(
NULL
,
(
EFI_DEVICE_PATH_PROTOCOL
*
)
TmpBuf
);
gBlockData
.
DevicePathCompareLen
=
sizeof
(
VENDOR_DEVICE_PATH
)
+
NameLen
;
debug
(
"gBlockData.Path=<%s>
\n
"
,
ConvertDevicePathToText
(
gBlockData
.
Path
,
FALSE
,
FALSE
));
return
EFI_SUCCESS
;
}
EFI_STATUS
EFIAPI
ventoy_connect_driver
(
IN
EFI_HANDLE
ControllerHandle
,
IN
CONST
CHAR16
*
DrvName
)
{
UINTN
i
=
0
;
UINTN
Count
=
0
;
CHAR16
*
DriverName
=
NULL
;
EFI_HANDLE
*
Handles
=
NULL
;
EFI_HANDLE
DrvHandles
[
2
]
=
{
NULL
};
EFI_STATUS
Status
=
EFI_SUCCESS
;
EFI_COMPONENT_NAME_PROTOCOL
*
NameProtocol
=
NULL
;
EFI_COMPONENT_NAME2_PROTOCOL
*
Name2Protocol
=
NULL
;
debug
(
"ventoy_connect_driver <%s>..."
,
DrvName
);
Status
=
gBS
->
LocateHandleBuffer
(
ByProtocol
,
&
gEfiComponentName2ProtocolGuid
,
NULL
,
&
Count
,
&
Handles
);
if
(
EFI_ERROR
(
Status
))
{
return
Status
;
}
for
(
i
=
0
;
i
<
Count
;
i
++
)
{
Status
=
gBS
->
HandleProtocol
(
Handles
[
i
],
&
gEfiComponentName2ProtocolGuid
,
(
VOID
**
)
&
Name2Protocol
);
if
(
EFI_ERROR
(
Status
))
{
continue
;
}
Status
=
Name2Protocol
->
GetDriverName
(
Name2Protocol
,
"en"
,
&
DriverName
);
if
(
EFI_ERROR
(
Status
)
||
NULL
==
DriverName
)
{
continue
;
}
if
(
StrStr
(
DriverName
,
DrvName
))
{
debug
(
"Find driver name2:<%s>: <%s>"
,
DriverName
,
DrvName
);
DrvHandles
[
0
]
=
Handles
[
i
];
break
;
}
}
if
(
i
<
Count
)
{
Status
=
gBS
->
ConnectController
(
ControllerHandle
,
DrvHandles
,
NULL
,
TRUE
);
debug
(
"Connect partition driver:<%r>"
,
Status
);
goto
end
;
}
debug
(
"%s NOT found, now try COMPONENT_NAME"
,
DrvName
);
Count
=
0
;
FreePool
(
Handles
);
Handles
=
NULL
;
Status
=
gBS
->
LocateHandleBuffer
(
ByProtocol
,
&
gEfiComponentNameProtocolGuid
,
NULL
,
&
Count
,
&
Handles
);
if
(
EFI_ERROR
(
Status
))
{
return
Status
;
}
for
(
i
=
0
;
i
<
Count
;
i
++
)
{
Status
=
gBS
->
HandleProtocol
(
Handles
[
i
],
&
gEfiComponentNameProtocolGuid
,
(
VOID
**
)
&
NameProtocol
);
if
(
EFI_ERROR
(
Status
))
{
continue
;
}
Status
=
NameProtocol
->
GetDriverName
(
NameProtocol
,
"en"
,
&
DriverName
);
if
(
EFI_ERROR
(
Status
))
{
continue
;
}
if
(
StrStr
(
DriverName
,
DrvName
))
{
debug
(
"Find driver name:<%s>: <%s>"
,
DriverName
,
DrvName
);
DrvHandles
[
0
]
=
Handles
[
i
];
break
;
}
}
if
(
i
<
Count
)
{
Status
=
gBS
->
ConnectController
(
ControllerHandle
,
DrvHandles
,
NULL
,
TRUE
);
debug
(
"Connect partition driver:<%r>"
,
Status
);
goto
end
;
}
Status
=
EFI_NOT_FOUND
;
end:
FreePool
(
Handles
);
return
Status
;
}
EFI_STATUS
EFIAPI
ventoy_install_blockio
(
IN
EFI_HANDLE
ImageHandle
,
IN
UINT64
ImgSize
)
{
EFI_STATUS
Status
=
EFI_SUCCESS
;
EFI_BLOCK_IO_PROTOCOL
*
pBlockIo
=
&
(
gBlockData
.
BlockIo
);
ventoy_fill_device_path
();
gBlockData
.
Media
.
BlockSize
=
2048
;
gBlockData
.
Media
.
LastBlock
=
ImgSize
/
2048
-
1
;
gBlockData
.
Media
.
ReadOnly
=
TRUE
;
gBlockData
.
Media
.
MediaPresent
=
1
;
gBlockData
.
Media
.
LogicalBlocksPerPhysicalBlock
=
1
;
pBlockIo
->
Revision
=
EFI_BLOCK_IO_PROTOCOL_REVISION3
;
pBlockIo
->
Media
=
&
(
gBlockData
.
Media
);
pBlockIo
->
Reset
=
ventoy_block_io_reset
;
pBlockIo
->
ReadBlocks
=
gMemdiskMode
?
ventoy_block_io_ramdisk_read
:
ventoy_block_io_read
;
pBlockIo
->
WriteBlocks
=
ventoy_block_io_write
;
pBlockIo
->
FlushBlocks
=
ventoy_block_io_flush
;
Status
=
gBS
->
InstallMultipleProtocolInterfaces
(
&
gBlockData
.
Handle
,
&
gEfiBlockIoProtocolGuid
,
&
gBlockData
.
BlockIo
,
&
gEfiDevicePathProtocolGuid
,
gBlockData
.
Path
,
NULL
);
debug
(
"Install protocol %r %p"
,
Status
,
gBlockData
.
Handle
);
if
(
EFI_ERROR
(
Status
))
{
return
Status
;
}
Status
=
ventoy_connect_driver
(
gBlockData
.
Handle
,
L"Disk I/O Driver"
);
debug
(
"Connect disk IO driver %r"
,
Status
);
ventoy_debug_pause
();
Status
=
ventoy_connect_driver
(
gBlockData
.
Handle
,
L"Partition Driver"
);
debug
(
"Connect partition driver %r"
,
Status
);
if
(
EFI_ERROR
(
Status
))
{
Status
=
gBS
->
ConnectController
(
gBlockData
.
Handle
,
NULL
,
NULL
,
TRUE
);
debug
(
"Connect all controller %r"
,
Status
);
}
ventoy_debug_pause
();
return
EFI_SUCCESS
;
}
EFI_STATUS
EFIAPI
ventoy_wrapper_file_open
(
EFI_FILE_HANDLE
This
,
EFI_FILE_HANDLE
*
New
,
CHAR16
*
Name
,
UINT64
Mode
,
UINT64
Attributes
)
{
UINT32
i
=
0
;
UINT32
j
=
0
;
UINT64
Sectors
=
0
;
EFI_STATUS
Status
=
EFI_SUCCESS
;
CHAR8
TmpName
[
256
];
ventoy_virt_chunk
*
virt
=
NULL
;
Status
=
g_original_fopen
(
This
,
New
,
Name
,
Mode
,
Attributes
);
if
(
EFI_ERROR
(
Status
))
{
return
Status
;
}
if
(
g_file_replace_list
&&
g_file_replace_list
->
magic
==
GRUB_FILE_REPLACE_MAGIC
&&
g_file_replace_list
->
new_file_virtual_id
<
g_virt_chunk_num
)
{
AsciiSPrint
(
TmpName
,
sizeof
(
TmpName
),
"%s"
,
Name
);
for
(
j
=
0
;
j
<
4
;
j
++
)
{
if
(
0
==
AsciiStrCmp
(
g_file_replace_list
[
i
].
old_file_name
[
j
],
TmpName
))
{
g_original_fclose
(
*
New
);
*
New
=
&
g_efi_file_replace
.
WrapperHandle
;
ventoy_wrapper_file_procotol
(
*
New
);
virt
=
g_virt_chunk
+
g_file_replace_list
->
new_file_virtual_id
;
Sectors
=
(
virt
->
mem_sector_end
-
virt
->
mem_sector_start
)
+
(
virt
->
remap_sector_end
-
virt
->
remap_sector_start
);
g_efi_file_replace
.
BlockIoSectorStart
=
virt
->
mem_sector_start
;
g_efi_file_replace
.
FileSizeBytes
=
Sectors
*
2048
;
if
(
gDebugPrint
)
{
debug
(
"## ventoy_wrapper_file_open <%s> BlockStart:%lu Sectors:%lu Bytes:%lu"
,
Name
,
g_efi_file_replace
.
BlockIoSectorStart
,
Sectors
,
Sectors
*
2048
);
sleep
(
3
);
}
return
Status
;
}
}
}
return
Status
;
}
EFI_STATUS
EFIAPI
ventoy_wrapper_open_volume
(
IN
EFI_SIMPLE_FILE_SYSTEM_PROTOCOL
*
This
,
OUT
EFI_FILE_PROTOCOL
**
Root
)
{
EFI_STATUS
Status
=
EFI_SUCCESS
;
Status
=
g_original_open_volume
(
This
,
Root
);
if
(
!
EFI_ERROR
(
Status
))
{
g_original_fopen
=
(
*
Root
)
->
Open
;
g_original_fclose
=
(
*
Root
)
->
Close
;
(
*
Root
)
->
Open
=
ventoy_wrapper_file_open
;
}
return
Status
;
}
EFI_STATUS
EFIAPI
ventoy_wrapper_push_openvolume
(
IN
EFI_SIMPLE_FILE_SYSTEM_PROTOCOL_OPEN_VOLUME
OpenVolume
)
{
g_original_open_volume
=
OpenVolume
;
return
EFI_SUCCESS
;
}
GRUB2/MOD_SRC/grub-2.04/grub-core/commands/test.c
0 → 100644
View file @
a5c70651
/* test.c -- The test command.. */
/*
* GRUB -- GRand Unified Bootloader
* Copyright (C) 2005,2007,2009 Free Software Foundation, Inc.
*
* GRUB is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* GRUB is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with GRUB. If not, see <http://www.gnu.org/licenses/>.
*/
#include <grub/dl.h>
#include <grub/misc.h>
#include <grub/mm.h>
#include <grub/env.h>
#include <grub/fs.h>
#include <grub/device.h>
#include <grub/file.h>
#include <grub/command.h>
#include <grub/i18n.h>
GRUB_MOD_LICENSE
(
"GPLv3+"
);
static
int
g_test_case_insensitive
=
0
;
/* A simple implementation for signed numbers. */
static
int
grub_strtosl
(
char
*
arg
,
char
**
end
,
int
base
)
{
if
(
arg
[
0
]
==
'-'
)
return
-
grub_strtoul
(
arg
+
1
,
end
,
base
);
return
grub_strtoul
(
arg
,
end
,
base
);
}
/* Context for test_parse. */
struct
test_parse_ctx
{
int
invert
;
int
or
,
and
;
int
file_exists
;
struct
grub_dirhook_info
file_info
;
char
*
filename
;
};
/* Take care of discarding and inverting. */
static
void
update_val
(
int
val
,
struct
test_parse_ctx
*
ctx
)
{
ctx
->
and
=
ctx
->
and
&&
(
ctx
->
invert
?
!
val
:
val
);
ctx
->
invert
=
0
;
}
/* A hook for iterating directories. */
static
int
find_file
(
const
char
*
cur_filename
,
const
struct
grub_dirhook_info
*
info
,
void
*
data
)
{
int
case_insensitive
=
0
;
struct
test_parse_ctx
*
ctx
=
data
;
if
(
g_test_case_insensitive
||
info
->
case_insensitive
)
case_insensitive
=
1
;
if
((
case_insensitive
?
grub_strcasecmp
(
cur_filename
,
ctx
->
filename
)
:
grub_strcmp
(
cur_filename
,
ctx
->
filename
))
==
0
)
{
ctx
->
file_info
=
*
info
;
ctx
->
file_exists
=
1
;
return
1
;
}
return
0
;
}
/* Check if file exists and fetch its information. */
static
void
get_fileinfo
(
char
*
path
,
struct
test_parse_ctx
*
ctx
)
{
char
*
pathname
;
char
*
device_name
;
grub_fs_t
fs
;
grub_device_t
dev
;
ctx
->
file_exists
=
0
;
device_name
=
grub_file_get_device_name
(
path
);
dev
=
grub_device_open
(
device_name
);
if
(
!
dev
)
{
grub_free
(
device_name
);
return
;
}
fs
=
grub_fs_probe
(
dev
);
if
(
!
fs
)
{
grub_free
(
device_name
);
grub_device_close
(
dev
);
return
;
}
pathname
=
grub_strchr
(
path
,
')'
);
if
(
!
pathname
)
pathname
=
path
;
else
pathname
++
;
/* Remove trailing '/'. */
while
(
*
pathname
&&
pathname
[
grub_strlen
(
pathname
)
-
1
]
==
'/'
)
pathname
[
grub_strlen
(
pathname
)
-
1
]
=
0
;
/* Split into path and filename. */
ctx
->
filename
=
grub_strrchr
(
pathname
,
'/'
);
if
(
!
ctx
->
filename
)
{
path
=
grub_strdup
(
"/"
);
ctx
->
filename
=
pathname
;
}
else
{
ctx
->
filename
++
;
path
=
grub_strdup
(
pathname
);
path
[
ctx
->
filename
-
pathname
]
=
0
;
}
/* It's the whole device. */
if
(
!
*
pathname
)
{
ctx
->
file_exists
=
1
;
grub_memset
(
&
ctx
->
file_info
,
0
,
sizeof
(
ctx
->
file_info
));
/* Root is always a directory. */
ctx
->
file_info
.
dir
=
1
;
/* Fetch writing time. */
ctx
->
file_info
.
mtimeset
=
0
;
if
(
fs
->
fs_mtime
)
{
if
(
!
fs
->
fs_mtime
(
dev
,
&
ctx
->
file_info
.
mtime
))
ctx
->
file_info
.
mtimeset
=
1
;
grub_errno
=
GRUB_ERR_NONE
;
}
}
else
(
fs
->
fs_dir
)
(
dev
,
path
,
find_file
,
ctx
);
grub_device_close
(
dev
);
grub_free
(
path
);
grub_free
(
device_name
);
}
/* Parse a test expression starting from *argn. */
static
int
test_parse
(
char
**
args
,
int
*
argn
,
int
argc
)
{
struct
test_parse_ctx
ctx
=
{
.
and
=
1
,
.
or
=
0
,
.
invert
=
0
};
/* Here we have the real parsing. */
while
(
*
argn
<
argc
)
{
/* First try 3 argument tests. */
if
(
*
argn
+
2
<
argc
)
{
/* String tests. */
if
(
grub_strcmp
(
args
[
*
argn
+
1
],
"="
)
==
0
||
grub_strcmp
(
args
[
*
argn
+
1
],
"=="
)
==
0
)
{
update_val
(
grub_strcmp
(
args
[
*
argn
],
args
[
*
argn
+
2
])
==
0
,
&
ctx
);
(
*
argn
)
+=
3
;
continue
;
}
if
(
grub_strcmp
(
args
[
*
argn
+
1
],
"!="
)
==
0
)
{
update_val
(
grub_strcmp
(
args
[
*
argn
],
args
[
*
argn
+
2
])
!=
0
,
&
ctx
);
(
*
argn
)
+=
3
;
continue
;
}
/* GRUB extension: lexicographical sorting. */
if
(
grub_strcmp
(
args
[
*
argn
+
1
],
"<"
)
==
0
)
{
update_val
(
grub_strcmp
(
args
[
*
argn
],
args
[
*
argn
+
2
])
<
0
,
&
ctx
);
(
*
argn
)
+=
3
;
continue
;
}
if
(
grub_strcmp
(
args
[
*
argn
+
1
],
"<="
)
==
0
)
{
update_val
(
grub_strcmp
(
args
[
*
argn
],
args
[
*
argn
+
2
])
<=
0
,
&
ctx
);
(
*
argn
)
+=
3
;
continue
;
}
if
(
grub_strcmp
(
args
[
*
argn
+
1
],
">"
)
==
0
)
{
update_val
(
grub_strcmp
(
args
[
*
argn
],
args
[
*
argn
+
2
])
>
0
,
&
ctx
);
(
*
argn
)
+=
3
;
continue
;
}
if
(
grub_strcmp
(
args
[
*
argn
+
1
],
">="
)
==
0
)
{
update_val
(
grub_strcmp
(
args
[
*
argn
],
args
[
*
argn
+
2
])
>=
0
,
&
ctx
);
(
*
argn
)
+=
3
;
continue
;
}
/* Number tests. */
if
(
grub_strcmp
(
args
[
*
argn
+
1
],
"-eq"
)
==
0
)
{
update_val
(
grub_strtosl
(
args
[
*
argn
],
0
,
0
)
==
grub_strtosl
(
args
[
*
argn
+
2
],
0
,
0
),
&
ctx
);
(
*
argn
)
+=
3
;
continue
;
}
if
(
grub_strcmp
(
args
[
*
argn
+
1
],
"-ge"
)
==
0
)
{
update_val
(
grub_strtosl
(
args
[
*
argn
],
0
,
0
)
>=
grub_strtosl
(
args
[
*
argn
+
2
],
0
,
0
),
&
ctx
);
(
*
argn
)
+=
3
;
continue
;
}
if
(
grub_strcmp
(
args
[
*
argn
+
1
],
"-gt"
)
==
0
)
{
update_val
(
grub_strtosl
(
args
[
*
argn
],
0
,
0
)
>
grub_strtosl
(
args
[
*
argn
+
2
],
0
,
0
),
&
ctx
);
(
*
argn
)
+=
3
;
continue
;
}
if
(
grub_strcmp
(
args
[
*
argn
+
1
],
"-le"
)
==
0
)
{
update_val
(
grub_strtosl
(
args
[
*
argn
],
0
,
0
)
<=
grub_strtosl
(
args
[
*
argn
+
2
],
0
,
0
),
&
ctx
);
(
*
argn
)
+=
3
;
continue
;
}
if
(
grub_strcmp
(
args
[
*
argn
+
1
],
"-lt"
)
==
0
)
{
update_val
(
grub_strtosl
(
args
[
*
argn
],
0
,
0
)
<
grub_strtosl
(
args
[
*
argn
+
2
],
0
,
0
),
&
ctx
);
(
*
argn
)
+=
3
;
continue
;
}
if
(
grub_strcmp
(
args
[
*
argn
+
1
],
"-ne"
)
==
0
)
{
update_val
(
grub_strtosl
(
args
[
*
argn
],
0
,
0
)
!=
grub_strtosl
(
args
[
*
argn
+
2
],
0
,
0
),
&
ctx
);
(
*
argn
)
+=
3
;
continue
;
}
/* GRUB extension: compare numbers skipping prefixes.
Useful for comparing versions. E.g. vmlinuz-2 -plt vmlinuz-11. */
if
(
grub_strcmp
(
args
[
*
argn
+
1
],
"-pgt"
)
==
0
||
grub_strcmp
(
args
[
*
argn
+
1
],
"-plt"
)
==
0
)
{
int
i
;
/* Skip common prefix. */
for
(
i
=
0
;
args
[
*
argn
][
i
]
==
args
[
*
argn
+
2
][
i
]
&&
args
[
*
argn
][
i
];
i
++
);
/* Go the digits back. */
i
--
;
while
(
grub_isdigit
(
args
[
*
argn
][
i
])
&&
i
>
0
)
i
--
;
i
++
;
if
(
grub_strcmp
(
args
[
*
argn
+
1
],
"-pgt"
)
==
0
)
update_val
(
grub_strtoul
(
args
[
*
argn
]
+
i
,
0
,
0
)
>
grub_strtoul
(
args
[
*
argn
+
2
]
+
i
,
0
,
0
),
&
ctx
);
else
update_val
(
grub_strtoul
(
args
[
*
argn
]
+
i
,
0
,
0
)
<
grub_strtoul
(
args
[
*
argn
+
2
]
+
i
,
0
,
0
),
&
ctx
);
(
*
argn
)
+=
3
;
continue
;
}
/* -nt and -ot tests. GRUB extension: when doing -?t<bias> bias
will be added to the first mtime. */
if
(
grub_memcmp
(
args
[
*
argn
+
1
],
"-nt"
,
3
)
==
0
||
grub_memcmp
(
args
[
*
argn
+
1
],
"-ot"
,
3
)
==
0
)
{
struct
grub_dirhook_info
file1
;
int
file1exists
;
int
bias
=
0
;
/* Fetch fileinfo. */
get_fileinfo
(
args
[
*
argn
],
&
ctx
);
file1
=
ctx
.
file_info
;
file1exists
=
ctx
.
file_exists
;
get_fileinfo
(
args
[
*
argn
+
2
],
&
ctx
);
if
(
args
[
*
argn
+
1
][
3
])
bias
=
grub_strtosl
(
args
[
*
argn
+
1
]
+
3
,
0
,
0
);
if
(
grub_memcmp
(
args
[
*
argn
+
1
],
"-nt"
,
3
)
==
0
)
update_val
((
file1exists
&&
!
ctx
.
file_exists
)
||
(
file1
.
mtimeset
&&
ctx
.
file_info
.
mtimeset
&&
file1
.
mtime
+
bias
>
ctx
.
file_info
.
mtime
),
&
ctx
);
else
update_val
((
!
file1exists
&&
ctx
.
file_exists
)
||
(
file1
.
mtimeset
&&
ctx
.
file_info
.
mtimeset
&&
file1
.
mtime
+
bias
<
ctx
.
file_info
.
mtime
),
&
ctx
);
(
*
argn
)
+=
3
;
continue
;
}
}
/* Two-argument tests. */
if
(
*
argn
+
1
<
argc
)
{
/* File tests. */
if
(
grub_strcmp
(
args
[
*
argn
],
"-d"
)
==
0
)
{
get_fileinfo
(
args
[
*
argn
+
1
],
&
ctx
);
update_val
(
ctx
.
file_exists
&&
ctx
.
file_info
.
dir
,
&
ctx
);
(
*
argn
)
+=
2
;
continue
;
}
if
(
grub_strcmp
(
args
[
*
argn
],
"-D"
)
==
0
)
{
g_test_case_insensitive
=
1
;
get_fileinfo
(
args
[
*
argn
+
1
],
&
ctx
);
g_test_case_insensitive
=
0
;
update_val
(
ctx
.
file_exists
&&
ctx
.
file_info
.
dir
,
&
ctx
);
(
*
argn
)
+=
2
;
continue
;
}
if
(
grub_strcmp
(
args
[
*
argn
],
"-e"
)
==
0
)
{
get_fileinfo
(
args
[
*
argn
+
1
],
&
ctx
);
update_val
(
ctx
.
file_exists
,
&
ctx
);
(
*
argn
)
+=
2
;
continue
;
}
if
(
grub_strcmp
(
args
[
*
argn
],
"-E"
)
==
0
)
{
g_test_case_insensitive
=
1
;
get_fileinfo
(
args
[
*
argn
+
1
],
&
ctx
);
g_test_case_insensitive
=
0
;
update_val
(
ctx
.
file_exists
,
&
ctx
);
(
*
argn
)
+=
2
;
continue
;
}
if
(
grub_strcmp
(
args
[
*
argn
],
"-f"
)
==
0
)
{
get_fileinfo
(
args
[
*
argn
+
1
],
&
ctx
);
/* FIXME: check for other types. */
update_val
(
ctx
.
file_exists
&&
!
ctx
.
file_info
.
dir
,
&
ctx
);
(
*
argn
)
+=
2
;
continue
;
}
if
(
grub_strcmp
(
args
[
*
argn
],
"-F"
)
==
0
)
{
g_test_case_insensitive
=
1
;
get_fileinfo
(
args
[
*
argn
+
1
],
&
ctx
);
g_test_case_insensitive
=
0
;
/* FIXME: check for other types. */
update_val
(
ctx
.
file_exists
&&
!
ctx
.
file_info
.
dir
,
&
ctx
);
(
*
argn
)
+=
2
;
continue
;
}
if
(
grub_strcmp
(
args
[
*
argn
],
"-s"
)
==
0
)
{
grub_file_t
file
;
file
=
grub_file_open
(
args
[
*
argn
+
1
],
GRUB_FILE_TYPE_GET_SIZE
|
GRUB_FILE_TYPE_NO_DECOMPRESS
);
update_val
(
file
&&
(
grub_file_size
(
file
)
!=
0
),
&
ctx
);
if
(
file
)
grub_file_close
(
file
);
grub_errno
=
GRUB_ERR_NONE
;
(
*
argn
)
+=
2
;
continue
;
}
/* String tests. */
if
(
grub_strcmp
(
args
[
*
argn
],
"-n"
)
==
0
)
{
update_val
(
args
[
*
argn
+
1
][
0
],
&
ctx
);
(
*
argn
)
+=
2
;
continue
;
}
if
(
grub_strcmp
(
args
[
*
argn
],
"-z"
)
==
0
)
{
update_val
(
!
args
[
*
argn
+
1
][
0
],
&
ctx
);
(
*
argn
)
+=
2
;
continue
;
}
}
/* Special modifiers. */
/* End of expression. return to parent. */
if
(
grub_strcmp
(
args
[
*
argn
],
")"
)
==
0
)
{
(
*
argn
)
++
;
return
ctx
.
or
||
ctx
.
and
;
}
/* Recursively invoke if parenthesis. */
if
(
grub_strcmp
(
args
[
*
argn
],
"("
)
==
0
)
{
(
*
argn
)
++
;
update_val
(
test_parse
(
args
,
argn
,
argc
),
&
ctx
);
continue
;
}
if
(
grub_strcmp
(
args
[
*
argn
],
"!"
)
==
0
)
{
ctx
.
invert
=
!
ctx
.
invert
;
(
*
argn
)
++
;
continue
;
}
if
(
grub_strcmp
(
args
[
*
argn
],
"-a"
)
==
0
)
{
(
*
argn
)
++
;
continue
;
}
if
(
grub_strcmp
(
args
[
*
argn
],
"-o"
)
==
0
)
{
ctx
.
or
=
ctx
.
or
||
ctx
.
and
;
ctx
.
and
=
1
;
(
*
argn
)
++
;
continue
;
}
/* No test found. Interpret if as just a string. */
update_val
(
args
[
*
argn
][
0
],
&
ctx
);
(
*
argn
)
++
;
}
return
ctx
.
or
||
ctx
.
and
;
}
static
grub_err_t
grub_cmd_test
(
grub_command_t
cmd
__attribute__
((
unused
)),
int
argc
,
char
**
args
)
{
int
argn
=
0
;
if
(
argc
>=
1
&&
grub_strcmp
(
args
[
argc
-
1
],
"]"
)
==
0
)
argc
--
;
return
test_parse
(
args
,
&
argn
,
argc
)
?
GRUB_ERR_NONE
:
grub_error
(
GRUB_ERR_TEST_FAILURE
,
N_
(
"false"
));
}
static
grub_command_t
cmd_1
,
cmd_2
;
GRUB_MOD_INIT
(
test
)
{
cmd_1
=
grub_register_command
(
"["
,
grub_cmd_test
,
N_
(
"EXPRESSION ]"
),
N_
(
"Evaluate an expression."
));
cmd_1
->
flags
|=
GRUB_COMMAND_FLAG_EXTRACTOR
;
cmd_2
=
grub_register_command
(
"test"
,
grub_cmd_test
,
N_
(
"EXPRESSION"
),
N_
(
"Evaluate an expression."
));
cmd_2
->
flags
|=
GRUB_COMMAND_FLAG_EXTRACTOR
;
}
GRUB_MOD_FINI
(
test
)
{
grub_unregister_command
(
cmd_1
);
grub_unregister_command
(
cmd_2
);
}
GRUB2/MOD_SRC/grub-2.04/grub-core/fs/fshelp.c
View file @
a5c70651
...
...
@@ -117,6 +117,8 @@ struct grub_fshelp_find_file_iter_ctx
enum
grub_fshelp_filetype
*
foundtype
;
};
int
g_ventoy_case_insensitive
=
0
;
/* Helper for grub_fshelp_find_file. */
static
int
find_file_iter
(
const
char
*
filename
,
enum
grub_fshelp_filetype
filetype
,
...
...
@@ -124,6 +126,11 @@ find_file_iter (const char *filename, enum grub_fshelp_filetype filetype,
{
struct
grub_fshelp_find_file_iter_ctx
*
ctx
=
data
;
if
(
g_ventoy_case_insensitive
)
{
filetype
|=
GRUB_FSHELP_CASE_INSENSITIVE
;
}
if
(
filetype
==
GRUB_FSHELP_UNKNOWN
||
((
filetype
&
GRUB_FSHELP_CASE_INSENSITIVE
)
?
grub_strcasecmp
(
ctx
->
name
,
filename
)
...
...
GRUB2/MOD_SRC/grub-2.04/grub-core/fs/iso9660.c
View file @
a5c70651
...
...
@@ -32,6 +32,7 @@
GRUB_MOD_LICENSE
(
"GPLv3+"
);
static
int
g_ventoy_no_joliet
=
0
;
static
grub_uint64_t
g_ventoy_last_read_pos
=
0
;
static
grub_uint64_t
g_ventoy_last_read_offset
=
0
;
static
grub_uint64_t
g_ventoy_last_read_dirent_pos
=
0
;
...
...
@@ -480,8 +481,10 @@ grub_iso9660_mount (grub_disk_t disk)
(
voldesc
.
escape
[
2
]
==
0x43
)
||
/* UCS-2 Level 2. */
(
voldesc
.
escape
[
2
]
==
0x45
)))
/* UCS-2 Level 3. */
{
copy_voldesc
=
1
;
data
->
joliet
=
1
;
if
(
0
==
g_ventoy_no_joliet
)
{
copy_voldesc
=
1
;
data
->
joliet
=
1
;
}
}
if
(
copy_voldesc
)
...
...
@@ -1108,6 +1111,11 @@ grub_iso9660_mtime (grub_device_t device, grub_int32_t *timebuf)
return
err
;
}
void
grub_iso9660_set_nojoliet
(
int
nojoliet
)
{
g_ventoy_no_joliet
=
nojoliet
;
}
grub_uint64_t
grub_iso9660_get_last_read_pos
(
grub_file_t
file
)
{
(
void
)
file
;
...
...
GRUB2/MOD_SRC/grub-2.04/grub-core/kern/disk.c
View file @
a5c70651
...
...
@@ -27,7 +27,7 @@
#include <grub/i18n.h>
#include <grub/ventoy.h>
#define GRUB_CACHE_TIMEOUT
2
#define GRUB_CACHE_TIMEOUT
10
/* The last time the disk was used. */
static
grub_uint64_t
grub_last_time
=
0
;
...
...
GRUB2/MOD_SRC/grub-2.04/grub-core/kern/file.c
View file @
a5c70651
...
...
@@ -83,6 +83,29 @@ grub_file_t grub_memfile_open(const char *name)
return
file
;
}
int
ventoy_check_file_exist
(
const
char
*
fmt
,
...)
{
va_list
ap
;
grub_file_t
file
;
char
fullpath
[
256
]
=
{
0
};
va_start
(
ap
,
fmt
);
grub_vsnprintf
(
fullpath
,
255
,
fmt
,
ap
);
va_end
(
ap
);
file
=
grub_file_open
(
fullpath
,
GRUB_FILE_TYPE_NONE
);
if
(
!
file
)
{
grub_errno
=
0
;
return
0
;
}
else
{
grub_file_close
(
file
);
return
1
;
}
}
grub_file_t
grub_file_open
(
const
char
*
name
,
enum
grub_file_type
type
)
{
...
...
GRUB2/MOD_SRC/grub-2.04/grub-core/kern/main.c
View file @
a5c70651
...
...
@@ -260,6 +260,45 @@ reclaim_module_space (void)
#endif
}
#ifndef GRUB_MACHINE_EFI
static
int
ventoy_legacy_limit_workaround
(
void
)
{
grub_file_t
file
;
char
*
pos
,
*
root
;
char
buf
[
128
];
root
=
grub_strdup
(
grub_env_get
(
"root"
));
if
(
!
root
)
{
return
1
;
}
pos
=
grub_strchr
(
root
,
','
);
if
(
pos
)
*
pos
=
0
;
grub_snprintf
(
buf
,
sizeof
(
buf
),
"(%s,1)/ventoy/ventoy.disk.img.xz"
,
root
);
file
=
grub_file_open
(
buf
,
GRUB_FILE_TYPE_NONE
);
if
(
file
)
{
pos
=
grub_malloc
(
file
->
size
);
if
(
pos
)
{
grub_file_read
(
file
,
pos
,
file
->
size
);
grub_snprintf
(
buf
,
sizeof
(
buf
),
"loopback ventoydisk mem:0x%lx:size:%lu"
,
(
unsigned
long
)
pos
,
(
unsigned
long
)
file
->
size
);
grub_parser_execute
(
buf
);
grub_env_set
(
"prefix"
,
"(ventoydisk)/grub"
);
}
grub_file_close
(
file
);
}
grub_free
(
root
);
return
0
;
}
#endif
/* The main routine. */
void
__attribute__
((
noreturn
))
grub_main
(
void
)
...
...
@@ -293,6 +332,12 @@ grub_main (void)
grub_env_export
(
"root"
);
grub_env_export
(
"prefix"
);
#ifndef GRUB_MACHINE_EFI
if
(
0
==
ventoy_check_file_exist
(
"%s/grub.cfg"
,
grub_env_get
(
"prefix"
)))
{
ventoy_legacy_limit_workaround
();
}
#endif
/* Reclaim space used for modules. */
reclaim_module_space
();
...
...
GRUB2/MOD_SRC/grub-2.04/grub-core/normal/menu.c
View file @
a5c70651
...
...
@@ -41,6 +41,7 @@ int g_ventoy_iso_uefi_drv = 0;
int
g_ventoy_last_entry
=
0
;
int
g_ventoy_suppress_esc
=
0
;
int
g_ventoy_menu_esc
=
0
;
int
g_ventoy_fn_mutex
=
0
;
/* Time to delay after displaying an error message about a default/fallback
entry failing to boot. */
...
...
@@ -802,39 +803,53 @@ run_menu (grub_menu_t menu, int nested, int *auto_boot)
goto
refresh
;
case
GRUB_TERM_KEY_F2
:
cmdstr
=
grub_env_get
(
"VTOY_F2_CMD"
);
if
(
cmdstr
)
{
menu_fini
();
grub_script_execute_sourcecode
(
cmdstr
);
goto
refresh
;
if
(
0
==
g_ventoy_fn_mutex
)
{
cmdstr
=
grub_env_get
(
"VTOY_F2_CMD"
);
if
(
cmdstr
)
{
menu_fini
();
g_ventoy_fn_mutex
=
1
;
grub_script_execute_sourcecode
(
cmdstr
);
g_ventoy_fn_mutex
=
0
;
goto
refresh
;
}
}
break
;
case
GRUB_TERM_KEY_F3
:
cmdstr
=
grub_env_get
(
"VTOY_F3_CMD"
);
if
(
cmdstr
)
{
menu_fini
();
grub_script_execute_sourcecode
(
cmdstr
);
goto
refresh
;
if
(
0
==
g_ventoy_fn_mutex
)
{
cmdstr
=
grub_env_get
(
"VTOY_F3_CMD"
);
if
(
cmdstr
)
{
menu_fini
();
grub_script_execute_sourcecode
(
cmdstr
);
goto
refresh
;
}
}
break
;
case
GRUB_TERM_KEY_F4
:
cmdstr
=
grub_env_get
(
"VTOY_F4_CMD"
);
if
(
cmdstr
)
{
menu_fini
();
grub_script_execute_sourcecode
(
cmdstr
);
goto
refresh
;
if
(
0
==
g_ventoy_fn_mutex
)
{
cmdstr
=
grub_env_get
(
"VTOY_F4_CMD"
);
if
(
cmdstr
)
{
menu_fini
();
g_ventoy_fn_mutex
=
1
;
grub_script_execute_sourcecode
(
cmdstr
);
g_ventoy_fn_mutex
=
0
;
goto
refresh
;
}
}
break
;
case
GRUB_TERM_KEY_F5
:
cmdstr
=
grub_env_get
(
"VTOY_F5_CMD"
);
if
(
cmdstr
)
{
menu_fini
();
grub_script_execute_sourcecode
(
cmdstr
);
goto
refresh
;
if
(
0
==
g_ventoy_fn_mutex
)
{
cmdstr
=
grub_env_get
(
"VTOY_F5_CMD"
);
if
(
cmdstr
)
{
menu_fini
();
g_ventoy_fn_mutex
=
1
;
grub_script_execute_sourcecode
(
cmdstr
);
g_ventoy_fn_mutex
=
0
;
goto
refresh
;
}
}
break
;
case
GRUB_TERM_KEY_F6
:
...
...
GRUB2/MOD_SRC/grub-2.04/grub-core/ventoy/ventoy.c
View file @
a5c70651
...
...
@@ -68,6 +68,7 @@ img_iterator_node *g_img_iterator_tail = NULL;
grub_uint8_t
g_ventoy_break_level
=
0
;
grub_uint8_t
g_ventoy_debug_level
=
0
;
grub_uint8_t
g_ventoy_chain_type
=
0
;
grub_uint8_t
*
g_ventoy_cpio_buf
=
NULL
;
grub_uint32_t
g_ventoy_cpio_size
=
0
;
cpio_newc_header
*
g_ventoy_initrd_head
=
NULL
;
...
...
@@ -433,6 +434,27 @@ static grub_err_t ventoy_cmd_load_iso_to_mem(grub_extcmd_context_t ctxt, int arg
return
rc
;
}
static
grub_err_t
ventoy_cmd_iso9660_nojoliet
(
grub_extcmd_context_t
ctxt
,
int
argc
,
char
**
args
)
{
(
void
)
ctxt
;
if
(
argc
!=
1
)
{
return
1
;
}
if
(
args
[
0
][
0
]
==
'1'
)
{
grub_iso9660_set_nojoliet
(
1
);
}
else
{
grub_iso9660_set_nojoliet
(
0
);
}
return
0
;
}
static
grub_err_t
ventoy_cmd_is_udf
(
grub_extcmd_context_t
ctxt
,
int
argc
,
char
**
args
)
{
int
i
;
...
...
@@ -853,6 +875,8 @@ static int ventoy_colect_img_files(const char *filename, const struct grub_dirho
*
((
img_info
**
)(
node
->
tail
))
=
img
;
g_ventoy_img_count
++
;
img
->
alias
=
ventoy_plugin_get_menu_alias
(
img
->
path
);
debug
(
"Add %s%s to list %d
\n
"
,
node
->
dir
,
filename
,
g_ventoy_img_count
);
}
}
...
...
@@ -1031,7 +1055,8 @@ static int ventoy_dynamic_tree_menu(img_iterator_node *node)
" %s_%s
\n
"
"}
\n
"
,
grub_get_human_size
(
img
->
size
,
GRUB_HUMAN_SIZE_SHORT
),
img
->
unsupport
?
"[unsupported] "
:
""
,
img
->
name
,
img
->
id
,
img
->
unsupport
?
"[unsupported] "
:
""
,
img
->
alias
?
img
->
alias
:
img
->
name
,
img
->
id
,
(
img
->
type
==
img_type_iso
)
?
"iso"
:
"wim"
,
img
->
unsupport
?
"unsupport_menuentry"
:
"common_menuentry"
);
}
...
...
@@ -1115,7 +1140,7 @@ static grub_err_t ventoy_cmd_list_img(grub_extcmd_context_t ctxt, int argc, char
if
(
strdata
&&
strdata
[
0
]
==
'/'
)
{
len
=
grub_snprintf
(
g_img_iterator_head
.
dir
,
sizeof
(
g_img_iterator_head
.
dir
)
-
1
,
"%s"
,
strdata
);
if
(
g_img_iterator_head
.
dir
[
len
]
!=
'/'
)
if
(
g_img_iterator_head
.
dir
[
len
-
1
]
!=
'/'
)
{
g_img_iterator_head
.
dir
[
len
++
]
=
'/'
;
}
...
...
@@ -1174,7 +1199,8 @@ static grub_err_t ventoy_cmd_list_img(grub_extcmd_context_t ctxt, int argc, char
"menuentry
\"
%s%s
\"
--id=
\"
VID_%d
\"
{
\n
"
" %s_%s
\n
"
"}
\n
"
,
cur
->
unsupport
?
"[unsupported] "
:
""
,
cur
->
name
,
cur
->
id
,
cur
->
unsupport
?
"[unsupported] "
:
""
,
cur
->
alias
?
cur
->
alias
:
cur
->
name
,
cur
->
id
,
(
cur
->
type
==
img_type_iso
)
?
"iso"
:
"wim"
,
cur
->
unsupport
?
"unsupport_menuentry"
:
"common_menuentry"
);
}
...
...
@@ -1394,6 +1420,7 @@ int ventoy_has_efi_eltorito(grub_file_t file, grub_uint32_t sector)
void
ventoy_fill_os_param
(
grub_file_t
file
,
ventoy_os_param
*
param
)
{
char
*
pos
;
const
char
*
fs
=
NULL
;
grub_uint32_t
i
;
grub_uint8_t
chksum
=
0
;
grub_disk_t
disk
;
...
...
@@ -1419,6 +1446,14 @@ void ventoy_fill_os_param(grub_file_t file, ventoy_os_param *param)
param
->
vtoy_reserved
[
0
]
=
g_ventoy_break_level
;
param
->
vtoy_reserved
[
1
]
=
g_ventoy_debug_level
;
param
->
vtoy_reserved
[
2
]
=
g_ventoy_chain_type
;
fs
=
ventoy_get_env
(
"ventoy_fs_probe"
);
if
(
fs
&&
grub_strcmp
(
fs
,
"udf"
)
==
0
)
{
param
->
vtoy_reserved
[
3
]
=
1
;
}
/* calculate checksum */
for
(
i
=
0
;
i
<
sizeof
(
ventoy_os_param
);
i
++
)
...
...
@@ -1567,6 +1602,8 @@ static grub_err_t ventoy_cmd_sel_auto_install(grub_extcmd_context_t ctxt, int ar
(
void
)
argc
;
(
void
)
args
;
debug
(
"select auto installation %d
\n
"
,
argc
);
if
(
argc
<
1
)
{
return
0
;
...
...
@@ -1575,6 +1612,7 @@ static grub_err_t ventoy_cmd_sel_auto_install(grub_extcmd_context_t ctxt, int ar
node
=
ventoy_plugin_find_install_template
(
args
[
0
]);
if
(
!
node
)
{
debug
(
"Install template not found for %s
\n
"
,
args
[
0
]);
return
0
;
}
...
...
@@ -1622,6 +1660,8 @@ static grub_err_t ventoy_cmd_sel_persistence(grub_extcmd_context_t ctxt, int arg
(
void
)
argc
;
(
void
)
args
;
debug
(
"select persistece %d
\n
"
,
argc
);
if
(
argc
<
1
)
{
return
0
;
...
...
@@ -1630,6 +1670,7 @@ static grub_err_t ventoy_cmd_sel_persistence(grub_extcmd_context_t ctxt, int arg
node
=
ventoy_plugin_find_persistent
(
args
[
0
]);
if
(
!
node
)
{
debug
(
"Persistence image not found for %s
\n
"
,
args
[
0
]);
return
0
;
}
...
...
@@ -1854,12 +1895,51 @@ static grub_err_t ventoy_cmd_dump_menu(grub_extcmd_context_t ctxt, int argc, cha
return
0
;
}
static
grub_err_t
ventoy_cmd_dump_img_list
(
grub_extcmd_context_t
ctxt
,
int
argc
,
char
**
args
)
{
img_info
*
cur
=
g_ventoy_img_list
;
(
void
)
ctxt
;
(
void
)
argc
;
(
void
)
args
;
while
(
cur
)
{
grub_printf
(
"path:<%s>
\n
"
,
cur
->
path
);
grub_printf
(
"name:<%s>
\n\n
"
,
cur
->
name
);
cur
=
cur
->
next
;
}
return
0
;
}
static
grub_err_t
ventoy_cmd_dump_auto_install
(
grub_extcmd_context_t
ctxt
,
int
argc
,
char
**
args
)
{
(
void
)
ctxt
;
(
void
)
argc
;
(
void
)
args
;
{
grub_file_t
file
;
char
*
buf
;
char
name
[
128
];
file
=
grub_file_open
(
"(hd0,1)/ventoy/ventoy.disk.img.xz"
,
GRUB_FILE_TYPE_NONE
);
if
(
file
)
{
grub_printf
(
"Open File OK (size:%llu)
\n
"
,
(
ulonglong
)
file
->
size
);
buf
=
grub_malloc
(
file
->
size
);
grub_file_read
(
file
,
buf
,
file
->
size
);
grub_file_close
(
file
);
grub_snprintf
(
name
,
sizeof
(
name
),
"mem:0x%llx:size:%llu"
,
(
ulonglong
)(
ulong
)
buf
,
(
ulonglong
)
file
->
size
);
grub_printf
(
"<%s>
\n
"
,
name
);
}
}
ventoy_plugin_dump_auto_install
();
return
0
;
...
...
@@ -1962,6 +2042,31 @@ static grub_err_t ventoy_cmd_dynamic_menu(grub_extcmd_context_t ctxt, int argc,
return
0
;
}
static
grub_err_t
ventoy_cmd_file_exist_nocase
(
grub_extcmd_context_t
ctxt
,
int
argc
,
char
**
args
)
{
grub_file_t
file
;
(
void
)
ctxt
;
if
(
argc
!=
1
)
{
return
1
;
}
g_ventoy_case_insensitive
=
1
;
file
=
grub_file_open
(
args
[
0
],
VENTOY_FILE_TYPE
);
g_ventoy_case_insensitive
=
0
;
grub_errno
=
0
;
if
(
file
)
{
grub_file_close
(
file
);
return
0
;
}
return
1
;
}
static
grub_err_t
ventoy_cmd_find_bootable_hdd
(
grub_extcmd_context_t
ctxt
,
int
argc
,
char
**
args
)
{
int
id
=
0
;
...
...
@@ -2109,6 +2214,8 @@ static int ventoy_env_init(void)
grub_env_set
(
"vtdebug_flag"
,
""
);
grub_env_export
(
"vtdebug_flag"
);
g_tree_script_buf
=
grub_malloc
(
VTOY_MAX_SCRIPT_BUF
);
g_list_script_buf
=
grub_malloc
(
VTOY_MAX_SCRIPT_BUF
);
...
...
@@ -2146,11 +2253,13 @@ static cmd_para ventoy_cmds[] =
{
"vt_dump_menu"
,
ventoy_cmd_dump_menu
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_dynamic_menu"
,
ventoy_cmd_dynamic_menu
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_check_mode"
,
ventoy_cmd_check_mode
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_dump_img_list"
,
ventoy_cmd_dump_img_list
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_dump_auto_install"
,
ventoy_cmd_dump_auto_install
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_dump_persistence"
,
ventoy_cmd_dump_persistence
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_select_auto_install"
,
ventoy_cmd_sel_auto_install
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_select_persistence"
,
ventoy_cmd_sel_persistence
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_iso9660_nojoliet"
,
ventoy_cmd_iso9660_nojoliet
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_is_udf"
,
ventoy_cmd_is_udf
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_file_size"
,
ventoy_cmd_file_size
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_load_iso_to_mem"
,
ventoy_cmd_load_iso_to_mem
,
0
,
NULL
,
""
,
""
,
NULL
},
...
...
@@ -2164,18 +2273,25 @@ static cmd_para ventoy_cmds[] =
{
"vt_linux_valid_initrd_count"
,
ventoy_cmd_valid_initrd_count
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_linux_locate_initrd"
,
ventoy_cmd_linux_locate_initrd
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_linux_chain_data"
,
ventoy_cmd_linux_chain_data
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_linux_get_main_initrd_index"
,
ventoy_cmd_linux_get_main_initrd_index
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_windows_reset"
,
ventoy_cmd_wimdows_reset
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_windows_locate_wim"
,
ventoy_cmd_wimdows_locate_wim
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_windows_chain_data"
,
ventoy_cmd_windows_chain_data
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_windows_collect_wim_patch"
,
ventoy_cmd_collect_wim_patch
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_windows_locate_wim_patch"
,
ventoy_cmd_locate_wim_patch
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_windows_count_wim_patch"
,
ventoy_cmd_wim_patch_count
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_dump_wim_patch"
,
ventoy_cmd_dump_wim_patch
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_wim_chain_data"
,
ventoy_cmd_wim_chain_data
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_add_replace_file"
,
ventoy_cmd_add_replace_file
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_relocator_chaindata"
,
ventoy_cmd_relocator_chaindata
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_test_block_list"
,
ventoy_cmd_test_block_list
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_file_exist_nocase"
,
ventoy_cmd_file_exist_nocase
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_load_plugin"
,
ventoy_cmd_load_plugin
,
0
,
NULL
,
""
,
""
,
NULL
},
{
"vt_check_plugin_json"
,
ventoy_cmd_plugin_check_json
,
0
,
NULL
,
""
,
""
,
NULL
},
};
...
...
GRUB2/MOD_SRC/grub-2.04/grub-core/ventoy/ventoy_def.h
View file @
a5c70651
...
...
@@ -132,6 +132,9 @@ typedef struct img_info
{
char
path
[
512
];
char
name
[
256
];
const
char
*
alias
;
int
id
;
int
type
;
grub_uint64_t
size
;
...
...
@@ -363,6 +366,19 @@ typedef struct wim_tail
grub_uint32_t
new_lookup_align_len
;
}
wim_tail
;
typedef
struct
wim_patch
{
int
pathlen
;
char
path
[
256
];
wim_hash
old_hash
;
wim_tail
wim_data
;
wim_lookup_entry
*
replace_look
;
int
valid
;
struct
wim_patch
*
next
;
}
wim_patch
;
typedef
enum
_JSON_TYPE
...
...
@@ -412,11 +428,13 @@ typedef struct _JSON_PARSE
}
typedef
int
(
*
ventoy_plugin_entry_pf
)(
VTOY_JSON
*
json
,
const
char
*
isodisk
);
typedef
int
(
*
ventoy_plugin_check_pf
)(
VTOY_JSON
*
json
,
const
char
*
isodisk
);
typedef
struct
plugin_entry
{
const
char
*
key
;
ventoy_plugin_entry_pf
entryfunc
;
ventoy_plugin_check_pf
checkfunc
;
}
plugin_entry
;
...
...
@@ -440,9 +458,9 @@ int ventoy_is_file_exist(const char *fmt, ...);
int
ventoy_fill_data
(
grub_uint32_t
buflen
,
char
*
buffer
);
grub_err_t
ventoy_cmd_load_plugin
(
grub_extcmd_context_t
ctxt
,
int
argc
,
char
**
args
);
grub_err_t
ventoy_cmd_wimdows_reset
(
grub_extcmd_context_t
ctxt
,
int
argc
,
char
**
args
);
grub_err_t
ventoy_cmd_wimdows_locate_wim
(
grub_extcmd_context_t
ctxt
,
int
argc
,
char
**
args
);
grub_err_t
ventoy_cmd_windows_chain_data
(
grub_extcmd_context_t
ctxt
,
int
argc
,
char
**
args
);
grub_err_t
ventoy_cmd_wim_chain_data
(
grub_extcmd_context_t
ctxt
,
int
argc
,
char
**
args
);
grub_err_t
ventoy_cmd_dump_wim_patch
(
grub_extcmd_context_t
ctxt
,
int
argc
,
char
**
args
);
VTOY_JSON
*
vtoy_json_find_item
(
...
...
@@ -596,12 +614,23 @@ typedef struct persistence_config
struct
persistence_config
*
next
;
}
persistence_config
;
typedef
struct
menu_alias
{
int
pathlen
;
char
isopath
[
256
];
char
alias
[
256
];
struct
menu_alias
*
next
;
}
menu_alias
;
extern
int
g_ventoy_menu_esc
;
extern
int
g_ventoy_suppress_esc
;
extern
int
g_ventoy_last_entry
;
extern
int
g_ventoy_memdisk_mode
;
extern
int
g_ventoy_iso_raw
;
extern
int
g_ventoy_iso_uefi_drv
;
extern
int
g_ventoy_case_insensitive
;
extern
grub_uint8_t
g_ventoy_chain_type
;
int
ventoy_cmp_img
(
img_info
*
img1
,
img_info
*
img2
);
void
ventoy_swap_img
(
img_info
*
img1
,
img_info
*
img2
);
...
...
@@ -611,9 +640,15 @@ persistence_config * ventoy_plugin_find_persistent(const char *isopath);
void
ventoy_plugin_dump_auto_install
(
void
);
int
ventoy_fill_windows_rtdata
(
void
*
buf
,
char
*
isopath
);
int
ventoy_plugin_get_persistent_chunklist
(
const
char
*
isopath
,
int
index
,
ventoy_img_chunk_list
*
chunk_list
);
const
char
*
ventoy_plugin_get_menu_alias
(
const
char
*
isopath
);
int
ventoy_get_block_list
(
grub_file_t
file
,
ventoy_img_chunk_list
*
chunklist
,
grub_disk_addr_t
start
);
int
ventoy_check_block_list
(
grub_file_t
file
,
ventoy_img_chunk_list
*
chunklist
,
grub_disk_addr_t
start
);
void
ventoy_plugin_dump_persistence
(
void
);
grub_err_t
ventoy_cmd_plugin_check_json
(
grub_extcmd_context_t
ctxt
,
int
argc
,
char
**
args
);
grub_err_t
ventoy_cmd_linux_get_main_initrd_index
(
grub_extcmd_context_t
ctxt
,
int
argc
,
char
**
args
);
grub_err_t
ventoy_cmd_collect_wim_patch
(
grub_extcmd_context_t
ctxt
,
int
argc
,
char
**
args
);
grub_err_t
ventoy_cmd_wim_patch_count
(
grub_extcmd_context_t
ctxt
,
int
argc
,
char
**
args
);
grub_err_t
ventoy_cmd_locate_wim_patch
(
grub_extcmd_context_t
ctxt
,
int
argc
,
char
**
args
);
#endif
/* __VENTOY_DEF_H__ */
GRUB2/MOD_SRC/grub-2.04/grub-core/ventoy/ventoy_json.c
View file @
a5c70651
...
...
@@ -42,6 +42,11 @@ static void json_debug(const char *fmt, ...)
{
va_list
args
;
if
(
g_ventoy_debug
==
0
)
{
return
;
}
va_start
(
args
,
fmt
);
grub_vprintf
(
fmt
,
args
);
va_end
(
args
);
...
...
GRUB2/MOD_SRC/grub-2.04/grub-core/ventoy/ventoy_linux.c
View file @
a5c70651
...
...
@@ -841,6 +841,50 @@ static grub_err_t ventoy_linux_locate_initrd(int filt, int *filtcnt)
}
grub_err_t
ventoy_cmd_linux_get_main_initrd_index
(
grub_extcmd_context_t
ctxt
,
int
argc
,
char
**
args
)
{
int
index
=
0
;
char
buf
[
32
];
initrd_info
*
node
=
NULL
;
(
void
)
ctxt
;
(
void
)
argc
;
(
void
)
args
;
if
(
argc
!=
1
)
{
return
1
;
}
if
(
g_initrd_img_count
==
1
)
{
ventoy_set_env
(
args
[
0
],
"0"
);
VENTOY_CMD_RETURN
(
GRUB_ERR_NONE
);
}
for
(
node
=
g_initrd_img_list
;
node
;
node
=
node
->
next
)
{
if
(
node
->
size
<=
0
)
{
continue
;
}
if
(
grub_strstr
(
node
->
name
,
"ucode"
)
||
grub_strstr
(
node
->
name
,
"-firmware"
))
{
index
++
;
continue
;
}
grub_snprintf
(
buf
,
sizeof
(
buf
),
"%d"
,
index
);
ventoy_set_env
(
args
[
0
],
buf
);
break
;
}
debug
(
"main initrd index:%d
\n
"
,
index
);
VENTOY_CMD_RETURN
(
GRUB_ERR_NONE
);
}
grub_err_t
ventoy_cmd_linux_locate_initrd
(
grub_extcmd_context_t
ctxt
,
int
argc
,
char
**
args
)
{
int
sizefilt
=
0
;
...
...
@@ -1100,6 +1144,7 @@ grub_err_t ventoy_cmd_linux_chain_data(grub_extcmd_context_t ctxt, int argc, cha
grub_memset
(
chain
,
0
,
sizeof
(
ventoy_chain_head
));
/* part 1: os parameter */
g_ventoy_chain_type
=
0
;
ventoy_fill_os_param
(
file
,
&
(
chain
->
os_param
));
/* part 2: chain head */
...
...
GRUB2/MOD_SRC/grub-2.04/grub-core/ventoy/ventoy_plugin.c
View file @
a5c70651
...
...
@@ -41,6 +41,46 @@ GRUB_MOD_LICENSE ("GPLv3+");
static
char
g_iso_disk_name
[
128
];
static
install_template
*
g_install_template_head
=
NULL
;
static
persistence_config
*
g_persistence_head
=
NULL
;
static
menu_alias
*
g_menu_alias_head
=
NULL
;
static
int
ventoy_plugin_control_check
(
VTOY_JSON
*
json
,
const
char
*
isodisk
)
{
int
rc
=
0
;
VTOY_JSON
*
pNode
=
NULL
;
VTOY_JSON
*
pChild
=
NULL
;
(
void
)
isodisk
;
if
(
json
->
enDataType
!=
JSON_TYPE_ARRAY
)
{
grub_printf
(
"Not array type %d
\n
"
,
json
->
enDataType
);
return
1
;
}
for
(
pNode
=
json
->
pstChild
;
pNode
;
pNode
=
pNode
->
pstNext
)
{
if
(
pNode
->
enDataType
==
JSON_TYPE_OBJECT
)
{
pChild
=
pNode
->
pstChild
;
if
(
pChild
->
enDataType
==
JSON_TYPE_STRING
)
{
grub_printf
(
"%s: %s
\n
"
,
pChild
->
pcName
,
pChild
->
unData
.
pcStrVal
);
}
else
{
grub_printf
(
"%s is NOT string type
\n
"
,
pChild
->
pcName
);
rc
=
1
;
}
}
else
{
grub_printf
(
"%s is not an object
\n
"
,
pNode
->
pcName
);
rc
=
1
;
}
}
return
rc
;
}
static
int
ventoy_plugin_control_entry
(
VTOY_JSON
*
json
,
const
char
*
isodisk
)
{
...
...
@@ -70,6 +110,64 @@ static int ventoy_plugin_control_entry(VTOY_JSON *json, const char *isodisk)
return
0
;
}
static
int
ventoy_plugin_theme_check
(
VTOY_JSON
*
json
,
const
char
*
isodisk
)
{
int
exist
=
0
;
const
char
*
value
;
value
=
vtoy_json_get_string_ex
(
json
->
pstChild
,
"file"
);
if
(
value
)
{
grub_printf
(
"file: %s
\n
"
,
value
);
if
(
value
[
0
]
==
'/'
)
{
exist
=
ventoy_is_file_exist
(
"%s%s"
,
isodisk
,
value
);
}
else
{
exist
=
ventoy_is_file_exist
(
"%s/ventoy/%s"
,
isodisk
,
value
);
}
if
(
exist
==
0
)
{
grub_printf
(
"Theme file %s does NOT exist
\n
"
,
value
);
return
1
;
}
}
value
=
vtoy_json_get_string_ex
(
json
->
pstChild
,
"gfxmode"
);
if
(
value
)
{
grub_printf
(
"gfxmode: %s
\n
"
,
value
);
}
value
=
vtoy_json_get_string_ex
(
json
->
pstChild
,
"display_mode"
);
if
(
value
)
{
grub_printf
(
"display_mode: %s
\n
"
,
value
);
}
value
=
vtoy_json_get_string_ex
(
json
->
pstChild
,
"ventoy_left"
);
if
(
value
)
{
grub_printf
(
"ventoy_left: %s
\n
"
,
value
);
}
value
=
vtoy_json_get_string_ex
(
json
->
pstChild
,
"ventoy_top"
);
if
(
value
)
{
grub_printf
(
"ventoy_top: %s
\n
"
,
value
);
}
value
=
vtoy_json_get_string_ex
(
json
->
pstChild
,
"ventoy_color"
);
if
(
value
)
{
grub_printf
(
"ventoy_color: %s
\n
"
,
value
);
}
return
0
;
}
static
int
ventoy_plugin_theme_entry
(
VTOY_JSON
*
json
,
const
char
*
isodisk
)
{
const
char
*
value
;
...
...
@@ -104,6 +202,13 @@ static int ventoy_plugin_theme_entry(VTOY_JSON *json, const char *isodisk)
grub_env_set
(
"vtoy_gfxmode"
,
value
);
}
value
=
vtoy_json_get_string_ex
(
json
->
pstChild
,
"display_mode"
);
if
(
value
)
{
debug
(
"display_mode %s
\n
"
,
value
);
grub_env_set
(
"vtoy_display_mode"
,
value
);
}
value
=
vtoy_json_get_string_ex
(
json
->
pstChild
,
"ventoy_left"
);
if
(
value
)
{
...
...
@@ -125,6 +230,92 @@ static int ventoy_plugin_theme_entry(VTOY_JSON *json, const char *isodisk)
return
0
;
}
static
int
ventoy_plugin_check_path
(
const
char
*
path
,
const
char
*
file
)
{
if
(
file
[
0
]
!=
'/'
)
{
grub_printf
(
"%s is NOT begin with '/'
\n
"
,
file
);
return
1
;
}
if
(
grub_strchr
(
file
,
'\\'
))
{
grub_printf
(
"%s contains invalid '
\\
'
\n
"
,
file
);
return
1
;
}
if
(
grub_strstr
(
file
,
"//"
))
{
grub_printf
(
"%s contains invalid double slash
\n
"
,
file
);
return
1
;
}
if
(
grub_strstr
(
file
,
"../"
))
{
grub_printf
(
"%s contains invalid '../'
\n
"
,
file
);
return
1
;
}
if
(
!
ventoy_is_file_exist
(
"%s%s"
,
path
,
file
))
{
grub_printf
(
"%s%s does NOT exist
\n
"
,
path
,
file
);
return
1
;
}
return
0
;
}
static
int
ventoy_plugin_check_fullpath
(
VTOY_JSON
*
json
,
const
char
*
isodisk
,
const
char
*
key
)
{
int
rc
=
0
;
int
ret
=
0
;
VTOY_JSON
*
node
=
json
;
VTOY_JSON
*
child
=
NULL
;
while
(
node
)
{
if
(
0
==
grub_strcmp
(
key
,
node
->
pcName
))
{
break
;
}
node
=
node
->
pstNext
;
}
if
(
!
node
)
{
return
1
;
}
if
(
JSON_TYPE_STRING
==
node
->
enDataType
)
{
ret
=
ventoy_plugin_check_path
(
isodisk
,
node
->
unData
.
pcStrVal
);
grub_printf
(
"%s: %s [%s]
\n
"
,
key
,
node
->
unData
.
pcStrVal
,
ret
?
"FAIL"
:
"OK"
);
}
else
if
(
JSON_TYPE_ARRAY
==
node
->
enDataType
)
{
for
(
child
=
node
->
pstChild
;
child
;
child
=
child
->
pstNext
)
{
if
(
JSON_TYPE_STRING
!=
child
->
enDataType
)
{
grub_printf
(
"Non string json type
\n
"
);
}
else
{
rc
=
ventoy_plugin_check_path
(
isodisk
,
child
->
unData
.
pcStrVal
);
grub_printf
(
"%s: %s [%s]
\n
"
,
key
,
child
->
unData
.
pcStrVal
,
rc
?
"FAIL"
:
"OK"
);
ret
+=
rc
;
}
}
}
return
ret
;
}
static
int
ventoy_plugin_parse_fullpath
(
VTOY_JSON
*
json
,
...
...
@@ -209,6 +400,46 @@ static int ventoy_plugin_parse_fullpath
return
rc
;
}
static
int
ventoy_plugin_auto_install_check
(
VTOY_JSON
*
json
,
const
char
*
isodisk
)
{
const
char
*
iso
=
NULL
;
VTOY_JSON
*
pNode
=
NULL
;
if
(
json
->
enDataType
!=
JSON_TYPE_ARRAY
)
{
grub_printf
(
"Not array type %d
\n
"
,
json
->
enDataType
);
return
1
;
}
for
(
pNode
=
json
->
pstChild
;
pNode
;
pNode
=
pNode
->
pstNext
)
{
if
(
pNode
->
enDataType
!=
JSON_TYPE_OBJECT
)
{
grub_printf
(
"NOT object type
\n
"
);
}
iso
=
vtoy_json_get_string_ex
(
pNode
->
pstChild
,
"image"
);
if
(
iso
)
{
if
(
0
==
ventoy_plugin_check_path
(
isodisk
,
iso
))
{
grub_printf
(
"image: %s [OK]
\n
"
,
iso
);
ventoy_plugin_check_fullpath
(
pNode
->
pstChild
,
isodisk
,
"template"
);
}
else
{
grub_printf
(
"image: %s [FAIL]
\n
"
,
iso
);
}
}
else
{
grub_printf
(
"image not found
\n
"
);
}
}
return
0
;
}
static
int
ventoy_plugin_auto_install_entry
(
VTOY_JSON
*
json
,
const
char
*
isodisk
)
{
int
pathnum
=
0
;
...
...
@@ -264,6 +495,45 @@ static int ventoy_plugin_auto_install_entry(VTOY_JSON *json, const char *isodisk
return
0
;
}
static
int
ventoy_plugin_persistence_check
(
VTOY_JSON
*
json
,
const
char
*
isodisk
)
{
const
char
*
iso
=
NULL
;
VTOY_JSON
*
pNode
=
NULL
;
if
(
json
->
enDataType
!=
JSON_TYPE_ARRAY
)
{
grub_printf
(
"Not array type %d
\n
"
,
json
->
enDataType
);
return
1
;
}
for
(
pNode
=
json
->
pstChild
;
pNode
;
pNode
=
pNode
->
pstNext
)
{
if
(
pNode
->
enDataType
!=
JSON_TYPE_OBJECT
)
{
grub_printf
(
"NOT object type
\n
"
);
}
iso
=
vtoy_json_get_string_ex
(
pNode
->
pstChild
,
"image"
);
if
(
iso
)
{
if
(
0
==
ventoy_plugin_check_path
(
isodisk
,
iso
))
{
grub_printf
(
"image: %s [OK]
\n
"
,
iso
);
ventoy_plugin_check_fullpath
(
pNode
->
pstChild
,
isodisk
,
"backend"
);
}
else
{
grub_printf
(
"image: %s [FAIL]
\n
"
,
iso
);
}
}
else
{
grub_printf
(
"image not found
\n
"
);
}
}
return
0
;
}
static
int
ventoy_plugin_persistence_entry
(
VTOY_JSON
*
json
,
const
char
*
isodisk
)
{
...
...
@@ -322,13 +592,93 @@ static int ventoy_plugin_persistence_entry(VTOY_JSON *json, const char *isodisk)
return
0
;
}
static
int
ventoy_plugin_menualias_check
(
VTOY_JSON
*
json
,
const
char
*
isodisk
)
{
const
char
*
iso
=
NULL
;
const
char
*
alias
=
NULL
;
VTOY_JSON
*
pNode
=
NULL
;
(
void
)
isodisk
;
if
(
json
->
enDataType
!=
JSON_TYPE_ARRAY
)
{
grub_printf
(
"Not array %d
\n
"
,
json
->
enDataType
);
return
1
;
}
for
(
pNode
=
json
->
pstChild
;
pNode
;
pNode
=
pNode
->
pstNext
)
{
iso
=
vtoy_json_get_string_ex
(
pNode
->
pstChild
,
"image"
);
alias
=
vtoy_json_get_string_ex
(
pNode
->
pstChild
,
"alias"
);
if
(
iso
&&
iso
[
0
]
==
'/'
&&
alias
)
{
grub_printf
(
"image: <%s>
\n
"
,
iso
);
grub_printf
(
"alias: <%s>
\n\n
"
,
alias
);
}
}
return
0
;
}
static
int
ventoy_plugin_menualias_entry
(
VTOY_JSON
*
json
,
const
char
*
isodisk
)
{
const
char
*
iso
=
NULL
;
const
char
*
alias
=
NULL
;
VTOY_JSON
*
pNode
=
NULL
;
menu_alias
*
node
=
NULL
;
menu_alias
*
next
=
NULL
;
(
void
)
isodisk
;
if
(
json
->
enDataType
!=
JSON_TYPE_ARRAY
)
{
debug
(
"Not array %d
\n
"
,
json
->
enDataType
);
return
0
;
}
if
(
g_menu_alias_head
)
{
for
(
node
=
g_menu_alias_head
;
node
;
node
=
next
)
{
next
=
node
->
next
;
grub_free
(
node
);
}
g_menu_alias_head
=
NULL
;
}
for
(
pNode
=
json
->
pstChild
;
pNode
;
pNode
=
pNode
->
pstNext
)
{
iso
=
vtoy_json_get_string_ex
(
pNode
->
pstChild
,
"image"
);
alias
=
vtoy_json_get_string_ex
(
pNode
->
pstChild
,
"alias"
);
if
(
iso
&&
iso
[
0
]
==
'/'
&&
alias
)
{
node
=
grub_zalloc
(
sizeof
(
menu_alias
));
if
(
node
)
{
node
->
pathlen
=
grub_snprintf
(
node
->
isopath
,
sizeof
(
node
->
isopath
),
"%s"
,
iso
);
grub_snprintf
(
node
->
alias
,
sizeof
(
node
->
alias
),
"%s"
,
alias
);
if
(
g_menu_alias_head
)
{
node
->
next
=
g_menu_alias_head
;
}
g_menu_alias_head
=
node
;
}
}
}
return
0
;
}
static
plugin_entry
g_plugin_entries
[]
=
{
{
"control"
,
ventoy_plugin_control_entry
},
{
"theme"
,
ventoy_plugin_theme_entry
},
{
"auto_install"
,
ventoy_plugin_auto_install_entry
},
{
"persistence"
,
ventoy_plugin_persistence_entry
},
{
"control"
,
ventoy_plugin_control_entry
,
ventoy_plugin_control_check
},
{
"theme"
,
ventoy_plugin_theme_entry
,
ventoy_plugin_theme_check
},
{
"auto_install"
,
ventoy_plugin_auto_install_entry
,
ventoy_plugin_auto_install_check
},
{
"persistence"
,
ventoy_plugin_persistence_entry
,
ventoy_plugin_persistence_check
},
{
"menu_alias"
,
ventoy_plugin_menualias_entry
,
ventoy_plugin_menualias_check
},
};
static
int
ventoy_parse_plugin_config
(
VTOY_JSON
*
json
,
const
char
*
isodisk
)
...
...
@@ -566,3 +916,100 @@ end:
return
rc
;
}
const
char
*
ventoy_plugin_get_menu_alias
(
const
char
*
isopath
)
{
menu_alias
*
node
=
NULL
;
int
len
=
(
int
)
grub_strlen
(
isopath
);
for
(
node
=
g_menu_alias_head
;
node
;
node
=
node
->
next
)
{
if
(
node
->
pathlen
==
len
&&
grub_strcmp
(
node
->
isopath
,
isopath
)
==
0
)
{
return
node
->
alias
;
}
}
return
NULL
;
}
grub_err_t
ventoy_cmd_plugin_check_json
(
grub_extcmd_context_t
ctxt
,
int
argc
,
char
**
args
)
{
int
i
=
0
;
int
ret
=
0
;
char
*
buf
=
NULL
;
grub_file_t
file
;
VTOY_JSON
*
node
=
NULL
;
VTOY_JSON
*
json
=
NULL
;
(
void
)
ctxt
;
if
(
argc
!=
3
)
{
return
0
;
}
file
=
ventoy_grub_file_open
(
VENTOY_FILE_TYPE
,
"%s/ventoy/ventoy.json"
,
args
[
0
]);
if
(
!
file
)
{
grub_printf
(
"Plugin json file /ventoy/ventoy.json does NOT exist.
\n
"
);
goto
end
;
}
buf
=
grub_malloc
(
file
->
size
+
1
);
if
(
!
buf
)
{
grub_printf
(
"Failed to malloc memory %lu.
\n
"
,
(
ulong
)(
file
->
size
+
1
));
goto
end
;
}
buf
[
file
->
size
]
=
0
;
grub_file_read
(
file
,
buf
,
file
->
size
);
json
=
vtoy_json_create
();
if
(
!
json
)
{
grub_printf
(
"Failed to create json
\n
"
);
goto
end
;
}
ret
=
vtoy_json_parse
(
json
,
buf
);
if
(
ret
)
{
grub_printf
(
"Syntax error detected in ventoy.json, please check it.
\n
"
);
goto
end
;
}
for
(
node
=
json
->
pstChild
;
node
;
node
=
node
->
pstNext
)
{
if
(
grub_strcmp
(
node
->
pcName
,
args
[
1
])
==
0
)
{
break
;
}
}
if
(
!
node
)
{
grub_printf
(
"%s is NOT found in ventoy.json
\n
"
,
args
[
1
]);
goto
end
;
}
for
(
i
=
0
;
i
<
(
int
)
ARRAY_SIZE
(
g_plugin_entries
);
i
++
)
{
if
(
grub_strcmp
(
g_plugin_entries
[
i
].
key
,
args
[
1
])
==
0
)
{
if
(
g_plugin_entries
[
i
].
checkfunc
)
{
ret
=
g_plugin_entries
[
i
].
checkfunc
(
node
,
args
[
2
]);
}
break
;
}
}
end:
check_free
(
file
,
grub_file_close
);
check_free
(
json
,
vtoy_json_destroy
);
grub_check_free
(
buf
);
return
0
;
}
GRUB2/MOD_SRC/grub-2.04/grub-core/ventoy/ventoy_windows.c
View file @
a5c70651
...
...
@@ -40,13 +40,229 @@
GRUB_MOD_LICENSE
(
"GPLv3+"
);
wim_hash
g_old_hash
;
wim_tail
g_wim_data
;
static
int
g_iso_fs_type
=
0
;
static
int
g_wim_total_patch_count
=
0
;
static
int
g_wim_valid_patch_count
=
0
;
static
wim_patch
*
g_wim_patch_head
=
NULL
;
static
wim_lookup_entry
*
g_replace_look
=
NULL
;
grub_uint8_t
g_temp_buf
[
512
]
;
grub_ssize_t
lzx_decompress
(
const
void
*
data
,
grub_size_t
len
,
void
*
buf
);
static
wim_patch
*
ventoy_find_wim_patch
(
const
char
*
path
)
{
int
len
=
(
int
)
grub_strlen
(
path
);
wim_patch
*
node
=
g_wim_patch_head
;
while
(
node
)
{
if
(
len
==
node
->
pathlen
&&
0
==
grub_strcmp
(
path
,
node
->
path
))
{
return
node
;
}
node
=
node
->
next
;
}
return
NULL
;
}
static
int
ventoy_collect_wim_patch
(
const
char
*
bcdfile
)
{
int
i
,
j
,
k
;
int
rc
=
1
;
grub_uint64_t
magic
;
grub_file_t
file
=
NULL
;
char
*
buf
=
NULL
;
wim_patch
*
node
=
NULL
;
char
c
;
grub_uint8_t
byte
;
char
valid
;
char
path
[
256
];
g_ventoy_case_insensitive
=
1
;
file
=
grub_file_open
(
bcdfile
,
VENTOY_FILE_TYPE
);
g_ventoy_case_insensitive
=
0
;
if
(
!
file
)
{
debug
(
"Failed to open file %s
\n
"
,
bcdfile
);
grub_errno
=
0
;
goto
end
;
}
buf
=
grub_malloc
(
file
->
size
+
8
);
if
(
!
buf
)
{
goto
end
;
}
grub_file_read
(
file
,
buf
,
file
->
size
);
for
(
i
=
0
;
i
<
(
int
)
file
->
size
-
8
;
i
++
)
{
if
(
buf
[
i
+
8
]
!=
0
)
{
continue
;
}
magic
=
*
(
grub_uint64_t
*
)(
buf
+
i
);
/* .wim .WIM .Wim */
if
((
magic
==
0x006D00690077002EULL
)
||
(
magic
==
0x004D00490057002EULL
)
||
(
magic
==
0x006D00690057002EULL
))
{
for
(
j
=
i
;
j
>
0
;
j
-=
2
)
{
if
(
*
(
grub_uint16_t
*
)(
buf
+
j
)
==
0
)
{
break
;
}
}
if
(
j
>
0
)
{
byte
=
(
grub_uint8_t
)(
*
(
grub_uint16_t
*
)(
buf
+
j
+
2
));
if
(
byte
!=
'/'
&&
byte
!=
'\\'
)
{
continue
;
}
valid
=
1
;
for
(
k
=
0
,
j
+=
2
;
k
<
(
int
)
sizeof
(
path
)
-
1
&&
j
<
i
+
8
;
j
+=
2
)
{
byte
=
(
grub_uint8_t
)(
*
(
grub_uint16_t
*
)(
buf
+
j
));
c
=
(
char
)
byte
;
if
(
byte
>
'~'
||
byte
<
' '
)
/* not printable */
{
valid
=
0
;
break
;
}
else
if
(
c
==
'\\'
)
{
c
=
'/'
;
}
path
[
k
++
]
=
c
;
}
path
[
k
++
]
=
0
;
debug
(
"@@@@ Find wim flag:<%s>
\n
"
,
path
);
if
(
0
==
valid
)
{
debug
(
"Invalid wim file %d
\n
"
,
k
);
}
else
if
(
NULL
==
ventoy_find_wim_patch
(
path
))
{
node
=
grub_zalloc
(
sizeof
(
wim_patch
));
if
(
node
)
{
node
->
pathlen
=
grub_snprintf
(
node
->
path
,
sizeof
(
node
->
path
),
"%s"
,
path
);
debug
(
"add patch <%s>
\n
"
,
path
);
if
(
g_wim_patch_head
)
{
node
->
next
=
g_wim_patch_head
;
}
g_wim_patch_head
=
node
;
g_wim_total_patch_count
++
;
}
}
else
{
debug
(
"wim <%s> already exist
\n
"
,
path
);
}
}
}
}
end:
check_free
(
file
,
grub_file_close
);
grub_check_free
(
buf
);
return
rc
;
}
grub_err_t
ventoy_cmd_wim_patch_count
(
grub_extcmd_context_t
ctxt
,
int
argc
,
char
**
args
)
{
char
buf
[
32
];
(
void
)
ctxt
;
(
void
)
argc
;
(
void
)
args
;
if
(
argc
==
1
)
{
grub_snprintf
(
buf
,
sizeof
(
buf
),
"%d"
,
g_wim_total_patch_count
);
ventoy_set_env
(
args
[
0
],
buf
);
}
return
0
;
}
grub_err_t
ventoy_cmd_collect_wim_patch
(
grub_extcmd_context_t
ctxt
,
int
argc
,
char
**
args
)
{
wim_patch
*
node
=
NULL
;
(
void
)
ctxt
;
(
void
)
argc
;
(
void
)
args
;
if
(
argc
!=
2
)
{
return
1
;
}
debug
(
"ventoy_cmd_collect_wim_patch %s %s
\n
"
,
args
[
0
],
args
[
1
]);
if
(
grub_strcmp
(
args
[
0
],
"bcd"
)
==
0
)
{
ventoy_collect_wim_patch
(
args
[
1
]);
return
0
;
}
if
(
NULL
==
ventoy_find_wim_patch
(
args
[
1
]))
{
node
=
grub_zalloc
(
sizeof
(
wim_patch
));
if
(
node
)
{
node
->
pathlen
=
grub_snprintf
(
node
->
path
,
sizeof
(
node
->
path
),
"%s"
,
args
[
1
]);
debug
(
"add patch <%s>
\n
"
,
args
[
1
]);
if
(
g_wim_patch_head
)
{
node
->
next
=
g_wim_patch_head
;
}
g_wim_patch_head
=
node
;
g_wim_total_patch_count
++
;
}
}
return
0
;
}
grub_err_t
ventoy_cmd_dump_wim_patch
(
grub_extcmd_context_t
ctxt
,
int
argc
,
char
**
args
)
{
int
i
=
0
;
wim_patch
*
node
=
NULL
;
(
void
)
ctxt
;
(
void
)
argc
;
(
void
)
args
;
for
(
node
=
g_wim_patch_head
;
node
;
node
=
node
->
next
)
{
grub_printf
(
"%d %s [%s]
\n
"
,
i
++
,
node
->
path
,
node
->
valid
?
"SUCCESS"
:
"FAIL"
);
}
return
0
;
}
static
int
wim_name_cmp
(
const
char
*
search
,
grub_uint16_t
*
name
,
grub_uint16_t
namelen
)
{
char
c1
=
vtoy_to_upper
(
*
search
);
...
...
@@ -96,16 +312,24 @@ static int ventoy_is_pe64(grub_uint8_t *buffer)
grub_err_t
ventoy_cmd_wimdows_reset
(
grub_extcmd_context_t
ctxt
,
int
argc
,
char
**
args
)
{
wim_patch
*
next
=
NULL
;
wim_patch
*
node
=
g_wim_patch_head
;
(
void
)
ctxt
;
(
void
)
argc
;
(
void
)
args
;
check_free
(
g_wim_data
.
jump_bin_data
,
grub_free
);
check_free
(
g_wim_data
.
new_meta_data
,
grub_free
);
check_free
(
g_wim_data
.
new_lookup_data
,
grub_free
);
grub_memset
(
&
g_wim_data
,
0
,
sizeof
(
g_wim_data
));
while
(
node
)
{
next
=
node
->
next
;
grub_free
(
node
);
node
=
next
;
}
g_wim_patch_head
=
NULL
;
g_wim_total_patch_count
=
0
;
g_wim_valid_patch_count
=
0
;
return
0
;
}
...
...
@@ -159,7 +383,7 @@ end:
return
0
;
}
static
int
ventoy_get_override_info
(
grub_file_t
file
)
static
int
ventoy_get_override_info
(
grub_file_t
file
,
wim_tail
*
wim_data
)
{
grub_uint32_t
start_block
;
grub_uint64_t
file_offset
;
...
...
@@ -169,7 +393,7 @@ static int ventoy_get_override_info(grub_file_t file)
if
(
grub_strcmp
(
file
->
fs
->
name
,
"iso9660"
)
==
0
)
{
g_wim_data
.
iso_type
=
0
;
g_
iso_fs_type
=
wim_data
->
iso_type
=
0
;
override_len
=
sizeof
(
ventoy_iso9660_override
);
override_offset
=
grub_iso9660_get_last_file_dirent_pos
(
file
)
+
2
;
...
...
@@ -181,7 +405,7 @@ static int ventoy_get_override_info(grub_file_t file)
}
else
{
g_wim_data
.
iso_type
=
1
;
g_
iso_fs_type
=
wim_data
->
iso_type
=
1
;
override_len
=
sizeof
(
ventoy_udf_override
);
override_offset
=
grub_udf_get_last_file_attr_offset
(
file
,
&
start_block
,
&
fe_entry_size_offset
);
...
...
@@ -191,11 +415,11 @@ static int ventoy_get_override_info(grub_file_t file)
(
ulonglong
)
file
->
size
,
(
ulonglong
)
override_offset
,
(
ulonglong
)
file_offset
,
start_block
);
}
g_
wim_data
.
file_offset
=
file_offset
;
g_
wim_data
.
udf_start_block
=
start_block
;
g_
wim_data
.
fe_entry_size_offset
=
fe_entry_size_offset
;
g_
wim_data
.
override_offset
=
override_offset
;
g_
wim_data
.
override_len
=
override_len
;
wim_data
->
file_offset
=
file_offset
;
wim_data
->
udf_start_block
=
start_block
;
wim_data
->
fe_entry_size_offset
=
fe_entry_size_offset
;
wim_data
->
override_offset
=
override_offset
;
wim_data
->
override_len
=
override_len
;
return
0
;
}
...
...
@@ -336,7 +560,7 @@ static wim_directory_entry * search_replace_wim_dirent(void *meta_data, wim_dire
{
wim_directory_entry
*
wim_dirent
=
NULL
;
const
char
*
winpeshl_path
[]
=
{
"Windows"
,
"System32"
,
"winpeshl.exe"
,
NULL
};
const
char
*
pecmd_path
[]
=
{
"Windows"
,
"System32"
,
"PECMD.exe"
,
NULL
};
//
const char *pecmd_path[] = { "Windows", "System32", "PECMD.exe", NULL };
wim_dirent
=
search_full_wim_dirent
(
meta_data
,
dir
,
winpeshl_path
);
if
(
wim_dirent
)
...
...
@@ -344,11 +568,13 @@ static wim_directory_entry * search_replace_wim_dirent(void *meta_data, wim_dire
return
wim_dirent
;
}
#if 0
wim_dirent = search_full_wim_dirent(meta_data, dir, pecmd_path);
if (wim_dirent)
{
return wim_dirent;
}
#endif
return
NULL
;
}
...
...
@@ -394,7 +620,7 @@ static wim_lookup_entry * ventoy_find_meta_entry(wim_header *header, wim_lookup_
return
NULL
;
}
static
int
ventoy_update_all_hash
(
void
*
meta_data
,
wim_directory_entry
*
dir
)
static
int
ventoy_update_all_hash
(
wim_patch
*
patch
,
void
*
meta_data
,
wim_directory_entry
*
dir
)
{
if
((
meta_data
==
NULL
)
||
(
dir
==
NULL
))
{
...
...
@@ -408,15 +634,15 @@ static int ventoy_update_all_hash(void *meta_data, wim_directory_entry *dir)
do
{
if
(
dir
->
subdir
==
0
&&
grub_memcmp
(
dir
->
hash
.
sha1
,
g_
old_hash
.
sha1
,
sizeof
(
wim_hash
))
==
0
)
if
(
dir
->
subdir
==
0
&&
grub_memcmp
(
dir
->
hash
.
sha1
,
patch
->
old_hash
.
sha1
,
sizeof
(
wim_hash
))
==
0
)
{
debug
(
"find target file, name_len:%u upadte hash
\n
"
,
dir
->
name_len
);
grub_memcpy
(
dir
->
hash
.
sha1
,
&
(
g_
wim_data
.
bin_hash
),
sizeof
(
wim_hash
));
grub_memcpy
(
dir
->
hash
.
sha1
,
&
(
patch
->
wim_data
.
bin_hash
),
sizeof
(
wim_hash
));
}
if
(
dir
->
subdir
)
{
ventoy_update_all_hash
(
meta_data
,
(
wim_directory_entry
*
)((
char
*
)
meta_data
+
dir
->
subdir
));
ventoy_update_all_hash
(
patch
,
meta_data
,
(
wim_directory_entry
*
)((
char
*
)
meta_data
+
dir
->
subdir
));
}
dir
=
(
wim_directory_entry
*
)((
char
*
)
dir
+
dir
->
len
);
...
...
@@ -425,7 +651,7 @@ static int ventoy_update_all_hash(void *meta_data, wim_directory_entry *dir)
return
0
;
}
static
int
ventoy_cat_exe_file_data
(
grub_uint32_t
exe_len
,
grub_uint8_t
*
exe_data
)
static
int
ventoy_cat_exe_file_data
(
wim_tail
*
wim_data
,
grub_uint32_t
exe_len
,
grub_uint8_t
*
exe_data
)
{
int
pe64
=
0
;
char
file
[
256
];
...
...
@@ -439,19 +665,19 @@ static int ventoy_cat_exe_file_data(grub_uint32_t exe_len, grub_uint8_t *exe_dat
ventoy_load_jump_exe
(
file
,
&
jump_data
,
&
jump_len
,
NULL
);
jump_align
=
ventoy_align
(
jump_len
,
16
);
g_
wim_data
.
jump_exe_len
=
jump_len
;
g_
wim_data
.
bin_raw_len
=
jump_align
+
sizeof
(
ventoy_os_param
)
+
sizeof
(
ventoy_windows_data
)
+
exe_len
;
g_
wim_data
.
bin_align_len
=
ventoy_align
(
g_
wim_data
.
bin_raw_len
,
2048
);
wim_data
->
jump_exe_len
=
jump_len
;
wim_data
->
bin_raw_len
=
jump_align
+
sizeof
(
ventoy_os_param
)
+
sizeof
(
ventoy_windows_data
)
+
exe_len
;
wim_data
->
bin_align_len
=
ventoy_align
(
wim_data
->
bin_raw_len
,
2048
);
g_
wim_data
.
jump_bin_data
=
grub_malloc
(
g_
wim_data
.
bin_align_len
);
if
(
g_
wim_data
.
jump_bin_data
)
wim_data
->
jump_bin_data
=
grub_malloc
(
wim_data
->
bin_align_len
);
if
(
wim_data
->
jump_bin_data
)
{
grub_memcpy
(
g_
wim_data
.
jump_bin_data
,
jump_data
,
jump_len
);
grub_memcpy
(
g_
wim_data
.
jump_bin_data
+
jump_align
+
sizeof
(
ventoy_os_param
)
+
sizeof
(
ventoy_windows_data
),
exe_data
,
exe_len
);
grub_memcpy
(
wim_data
->
jump_bin_data
,
jump_data
,
jump_len
);
grub_memcpy
(
wim_data
->
jump_bin_data
+
jump_align
+
sizeof
(
ventoy_os_param
)
+
sizeof
(
ventoy_windows_data
),
exe_data
,
exe_len
);
}
debug
(
"jump_exe_len:%u bin_raw_len:%u bin_align_len:%u
\n
"
,
g_
wim_data
.
jump_exe_len
,
g_
wim_data
.
bin_raw_len
,
g_
wim_data
.
bin_align_len
);
wim_data
->
jump_exe_len
,
wim_data
->
bin_raw_len
,
wim_data
->
bin_align_len
);
return
0
;
}
...
...
@@ -490,49 +716,63 @@ static int ventoy_update_before_chain(ventoy_os_param *param, char *isopath)
wim_lookup_entry
*
meta_look
=
NULL
;
wim_security_header
*
security
=
NULL
;
wim_directory_entry
*
rootdir
=
NULL
;
wim_header
*
head
=
&
(
g_wim_data
.
wim_header
);
wim_lookup_entry
*
lookup
=
(
wim_lookup_entry
*
)
g_wim_data
.
new_lookup_data
;
wim_header
*
head
=
NULL
;
wim_lookup_entry
*
lookup
=
NULL
;
wim_patch
*
node
=
NULL
;
wim_tail
*
wim_data
=
NULL
;
jump_align
=
ventoy_align
(
g_wim_data
.
jump_exe_len
,
16
);
if
(
g_wim_data
.
jump_bin_data
)
for
(
node
=
g_wim_patch_head
;
node
;
node
=
node
->
next
)
{
grub_memcpy
(
g_wim_data
.
jump_bin_data
+
jump_align
,
param
,
sizeof
(
ventoy_os_param
));
ventoy_fill_windows_rtdata
(
g_wim_data
.
jump_bin_data
+
jump_align
+
sizeof
(
ventoy_os_param
),
isopath
);
}
if
(
0
==
node
->
valid
)
{
continue
;
}
grub_crypto_hash
(
GRUB_MD_SHA1
,
g_wim_data
.
bin_hash
.
sha1
,
g_wim_data
.
jump_bin_data
,
g_wim_data
.
bin_raw_len
);
wim_data
=
&
node
->
wim_data
;
head
=
&
wim_data
->
wim_header
;
lookup
=
(
wim_lookup_entry
*
)
wim_data
->
new_lookup_data
;
security
=
(
wim_security_header
*
)
g_wim_data
.
new_meta_data
;
rootdir
=
(
wim_directory_entry
*
)(
g_wim_data
.
new_meta_data
+
((
security
->
len
+
7
)
&
0xFFFFFFF8U
));
jump_align
=
ventoy_align
(
wim_data
->
jump_exe_len
,
16
);
if
(
wim_data
->
jump_bin_data
)
{
grub_memcpy
(
wim_data
->
jump_bin_data
+
jump_align
,
param
,
sizeof
(
ventoy_os_param
));
ventoy_fill_windows_rtdata
(
wim_data
->
jump_bin_data
+
jump_align
+
sizeof
(
ventoy_os_param
),
isopath
);
}
/* update all winpeshl.exe dirent entry's hash */
ventoy_update_all_hash
(
g_wim_data
.
new_meta_data
,
rootdir
);
grub_crypto_hash
(
GRUB_MD_SHA1
,
wim_data
->
bin_hash
.
sha1
,
wim_data
->
jump_bin_data
,
wim_data
->
bin_raw_len
);
/* update winpeshl.exe lookup entry data (hash/offset/length) */
if
(
g_replace_look
)
{
debug
(
"update replace lookup entry_id:%ld
\n
"
,
((
long
)
g_replace_look
-
(
long
)
lookup
)
/
sizeof
(
wim_lookup_entry
));
g_replace_look
->
resource
.
raw_size
=
g_wim_data
.
bin_raw_len
;
g_replace_look
->
resource
.
size_in_wim
=
g_wim_data
.
bin_raw_len
;
g_replace_look
->
resource
.
flags
=
0
;
g_replace_look
->
resource
.
offset
=
g_wim_data
.
wim_align_size
;
security
=
(
wim_security_header
*
)
wim_data
->
new_meta_data
;
rootdir
=
(
wim_directory_entry
*
)(
wim_data
->
new_meta_data
+
((
security
->
len
+
7
)
&
0xFFFFFFF8U
));
grub_memcpy
(
g_replace_look
->
hash
.
sha1
,
g_wim_data
.
bin_hash
.
sha1
,
sizeof
(
wim_
hash
));
}
/* update all winpeshl.exe dirent entry's
hash
*/
ventoy_update_all_hash
(
node
,
wim_data
->
new_meta_data
,
rootdir
);
/* update metadata's hash */
meta_look
=
ventoy_find_meta_entry
(
head
,
lookup
);
if
(
meta_look
)
{
debug
(
"find meta lookup entry_id:%ld
\n
"
,
((
long
)
meta_look
-
(
long
)
lookup
)
/
sizeof
(
wim_lookup_entry
));
grub_memcpy
(
&
meta_look
->
resource
,
&
head
->
metadata
,
sizeof
(
wim_resource_header
));
grub_crypto_hash
(
GRUB_MD_SHA1
,
meta_look
->
hash
.
sha1
,
g_wim_data
.
new_meta_data
,
g_wim_data
.
new_meta_len
);
/* update winpeshl.exe lookup entry data (hash/offset/length) */
if
(
node
->
replace_look
)
{
debug
(
"update replace lookup entry_id:%ld
\n
"
,
((
long
)
node
->
replace_look
-
(
long
)
lookup
)
/
sizeof
(
wim_lookup_entry
));
node
->
replace_look
->
resource
.
raw_size
=
wim_data
->
bin_raw_len
;
node
->
replace_look
->
resource
.
size_in_wim
=
wim_data
->
bin_raw_len
;
node
->
replace_look
->
resource
.
flags
=
0
;
node
->
replace_look
->
resource
.
offset
=
wim_data
->
wim_align_size
;
grub_memcpy
(
node
->
replace_look
->
hash
.
sha1
,
wim_data
->
bin_hash
.
sha1
,
sizeof
(
wim_hash
));
}
/* update metadata's hash */
meta_look
=
ventoy_find_meta_entry
(
head
,
lookup
);
if
(
meta_look
)
{
debug
(
"find meta lookup entry_id:%ld
\n
"
,
((
long
)
meta_look
-
(
long
)
lookup
)
/
sizeof
(
wim_lookup_entry
));
grub_memcpy
(
&
meta_look
->
resource
,
&
head
->
metadata
,
sizeof
(
wim_resource_header
));
grub_crypto_hash
(
GRUB_MD_SHA1
,
meta_look
->
hash
.
sha1
,
wim_data
->
new_meta_data
,
wim_data
->
new_meta_len
);
}
}
return
0
;
}
grub_err_
t
ventoy_
cmd_
wimdows_locate_wim
(
grub_extcmd_context_t
ctxt
,
int
argc
,
char
**
args
)
static
in
t
ventoy_wimdows_locate_wim
(
const
char
*
disk
,
wim_patch
*
patch
)
{
int
rc
;
grub_file_t
file
;
...
...
@@ -543,20 +783,22 @@ grub_err_t ventoy_cmd_wimdows_locate_wim(grub_extcmd_context_t ctxt, int argc, c
wim_security_header
*
security
=
NULL
;
wim_directory_entry
*
rootdir
=
NULL
;
wim_directory_entry
*
search
=
NULL
;
wim_header
*
head
=
&
(
g_wim_data
.
wim_header
);
wim_header
*
head
=
&
(
patch
->
wim_data
.
wim_header
);
wim_tail
*
wim_data
=
&
patch
->
wim_data
;
(
void
)
ctxt
;
(
void
)
argc
;
debug
(
"windows locate wim start %s
\n
"
,
patch
->
path
);
debug
(
"windows locate wim start %s
\n
"
,
args
[
0
]);
g_ventoy_case_insensitive
=
1
;
file
=
ventoy_grub_file_open
(
VENTOY_FILE_TYPE
,
"%s%s"
,
disk
,
patch
->
path
);
g_ventoy_case_insensitive
=
0
;
file
=
ventoy_grub_file_open
(
VENTOY_FILE_TYPE
,
"%s"
,
args
[
0
]);
if
(
!
file
)
{
return
grub_error
(
GRUB_ERR_BAD_ARGUMENT
,
"Can't open file %s
\n
"
,
args
[
0
]);
debug
(
"File %s%s NOT exist
\n
"
,
disk
,
patch
->
path
);
return
1
;
}
ventoy_get_override_info
(
file
);
ventoy_get_override_info
(
file
,
&
patch
->
wim_data
);
grub_file_seek
(
file
,
0
);
grub_file_read
(
file
,
head
,
sizeof
(
wim_header
));
...
...
@@ -596,8 +838,8 @@ grub_err_t ventoy_cmd_wimdows_locate_wim(grub_extcmd_context_t ctxt, int argc, c
}
debug
(
"find replace file at %p
\n
"
,
search
);
grub_memcpy
(
&
g_
old_hash
,
search
->
hash
.
sha1
,
sizeof
(
wim_hash
));
grub_memcpy
(
&
patch
->
old_hash
,
search
->
hash
.
sha1
,
sizeof
(
wim_hash
));
debug
(
"read lookup offset:%llu size:%llu
\n
"
,
(
ulonglong
)
head
->
lookup
.
offset
,
(
ulonglong
)
head
->
lookup
.
raw_size
);
lookup
=
grub_malloc
(
head
->
lookup
.
raw_size
);
...
...
@@ -605,16 +847,16 @@ grub_err_t ventoy_cmd_wimdows_locate_wim(grub_extcmd_context_t ctxt, int argc, c
grub_file_read
(
file
,
lookup
,
head
->
lookup
.
raw_size
);
/* find and extact winpeshl.exe */
g_
replace_look
=
ventoy_find_look_entry
(
head
,
lookup
,
&
g_
old_hash
);
if
(
g_
replace_look
)
patch
->
replace_look
=
ventoy_find_look_entry
(
head
,
lookup
,
&
patch
->
old_hash
);
if
(
patch
->
replace_look
)
{
exe_len
=
(
grub_uint32_t
)
g_
replace_look
->
resource
.
raw_size
;
exe_len
=
(
grub_uint32_t
)
patch
->
replace_look
->
resource
.
raw_size
;
debug
(
"find replace lookup entry_id:%ld raw_size:%u
\n
"
,
((
long
)
g_
replace_look
-
(
long
)
lookup
)
/
sizeof
(
wim_lookup_entry
),
exe_len
);
((
long
)
patch
->
replace_look
-
(
long
)
lookup
)
/
sizeof
(
wim_lookup_entry
),
exe_len
);
if
(
0
==
ventoy_read_resource
(
file
,
&
(
g_
replace_look
->
resource
),
(
void
**
)
&
(
exe_data
)))
if
(
0
==
ventoy_read_resource
(
file
,
&
(
patch
->
replace_look
->
resource
),
(
void
**
)
&
(
exe_data
)))
{
ventoy_cat_exe_file_data
(
exe_len
,
exe_data
);
ventoy_cat_exe_file_data
(
wim_data
,
exe_len
,
exe_data
);
grub_free
(
exe_data
);
}
else
...
...
@@ -624,106 +866,236 @@ grub_err_t ventoy_cmd_wimdows_locate_wim(grub_extcmd_context_t ctxt, int argc, c
}
else
{
debug
(
"failed to find lookup entry for replace file 0x%02x 0x%02x
\n
"
,
g_old_hash
.
sha1
[
0
],
g_old_hash
.
sha1
[
1
]);
debug
(
"failed to find lookup entry for replace file 0x%02x 0x%02x
\n
"
,
patch
->
old_hash
.
sha1
[
0
],
patch
->
old_hash
.
sha1
[
1
]);
}
g_
wim_data
.
wim_raw_size
=
(
grub_uint32_t
)
file
->
size
;
g_
wim_data
.
wim_align_size
=
ventoy_align
(
g_
wim_data
.
wim_raw_size
,
2048
);
wim_data
->
wim_raw_size
=
(
grub_uint32_t
)
file
->
size
;
wim_data
->
wim_align_size
=
ventoy_align
(
wim_data
->
wim_raw_size
,
2048
);
check_free
(
g_
wim_data
.
new_meta_data
,
grub_free
);
g_
wim_data
.
new_meta_data
=
decompress_data
;
g_
wim_data
.
new_meta_len
=
head
->
metadata
.
raw_size
;
g_
wim_data
.
new_meta_align_len
=
ventoy_align
(
g_
wim_data
.
new_meta_len
,
2048
);
grub_
check_free
(
wim_data
->
new_meta_data
);
wim_data
->
new_meta_data
=
decompress_data
;
wim_data
->
new_meta_len
=
head
->
metadata
.
raw_size
;
wim_data
->
new_meta_align_len
=
ventoy_align
(
wim_data
->
new_meta_len
,
2048
);
check_free
(
g_
wim_data
.
new_lookup_data
,
grub_free
);
g_
wim_data
.
new_lookup_data
=
(
grub_uint8_t
*
)
lookup
;
g_
wim_data
.
new_lookup_len
=
(
grub_uint32_t
)
head
->
lookup
.
raw_size
;
g_
wim_data
.
new_lookup_align_len
=
ventoy_align
(
g_
wim_data
.
new_lookup_len
,
2048
);
grub_
check_free
(
wim_data
->
new_lookup_data
);
wim_data
->
new_lookup_data
=
(
grub_uint8_t
*
)
lookup
;
wim_data
->
new_lookup_len
=
(
grub_uint32_t
)
head
->
lookup
.
raw_size
;
wim_data
->
new_lookup_align_len
=
ventoy_align
(
wim_data
->
new_lookup_len
,
2048
);
head
->
metadata
.
flags
=
RESHDR_FLAG_METADATA
;
head
->
metadata
.
offset
=
g_
wim_data
.
wim_align_size
+
g_
wim_data
.
bin_align_len
;
head
->
metadata
.
size_in_wim
=
g_
wim_data
.
new_meta_len
;
head
->
metadata
.
raw_size
=
g_
wim_data
.
new_meta_len
;
head
->
metadata
.
offset
=
wim_data
->
wim_align_size
+
wim_data
->
bin_align_len
;
head
->
metadata
.
size_in_wim
=
wim_data
->
new_meta_len
;
head
->
metadata
.
raw_size
=
wim_data
->
new_meta_len
;
head
->
lookup
.
flags
=
0
;
head
->
lookup
.
offset
=
head
->
metadata
.
offset
+
g_
wim_data
.
new_meta_align_len
;
head
->
lookup
.
size_in_wim
=
g_
wim_data
.
new_lookup_len
;
head
->
lookup
.
raw_size
=
g_
wim_data
.
new_lookup_len
;
head
->
lookup
.
offset
=
head
->
metadata
.
offset
+
wim_data
->
new_meta_align_len
;
head
->
lookup
.
size_in_wim
=
wim_data
->
new_lookup_len
;
head
->
lookup
.
raw_size
=
wim_data
->
new_lookup_len
;
grub_file_close
(
file
);
debug
(
"%s"
,
"windows locate wim finish
\n
"
);
VENTOY_CMD_RETURN
(
GRUB_ERR_NONE
);
return
0
;
}
grub_err_t
ventoy_cmd_locate_wim_patch
(
grub_extcmd_context_t
ctxt
,
int
argc
,
char
**
args
)
{
wim_patch
*
node
=
g_wim_patch_head
;
(
void
)
ctxt
;
(
void
)
argc
;
(
void
)
args
;
while
(
node
)
{
if
(
0
==
ventoy_wimdows_locate_wim
(
args
[
0
],
node
))
{
node
->
valid
=
1
;
g_wim_valid_patch_count
++
;
}
node
=
node
->
next
;
}
return
0
;
}
static
grub_uint32_t
ventoy_get_override_chunk_num
(
void
)
{
/* 1: block count in Partition Descriptor */
/* 2: file_size in file_entry or extend_file_entry */
/* 3: data_size and position in extend data short ad */
/* 4: new wim file header */
return
4
;
if
(
g_iso_fs_type
==
0
)
{
/* ISO9660: */
/* per wim */
/* 1: file_size and file_offset */
/* 2: new wim file header */
return
g_wim_valid_patch_count
*
2
;
}
else
{
/* UDF: */
/* global: */
/* 1: block count in Partition Descriptor */
/* per wim */
/* 1: file_size in file_entry or extend_file_entry */
/* 2: data_size and position in extend data short ad */
/* 3: new wim file header */
return
g_wim_valid_patch_count
*
3
+
1
;
}
}
static
void
ventoy_windows_fill_override_data
(
grub_uint64_t
isosize
,
void
*
override
)
static
void
ventoy_windows_fill_override_data
_iso9660
(
grub_uint64_t
isosize
,
void
*
override
)
{
grub_uint32_t
data32
;
grub_uint64_t
data64
;
grub_uint64_t
sector
;
grub_uint32_t
new_wim_size
;
ventoy_override_chunk
*
cur
;
wim_patch
*
node
=
NULL
;
wim_tail
*
wim_data
=
NULL
;
ventoy_iso9660_override
*
dirent
=
NULL
;
sector
=
(
isosize
+
2047
)
/
2048
;
cur
=
(
ventoy_override_chunk
*
)
override
;
new_wim_size
=
g_wim_data
.
wim_align_size
+
g_wim_data
.
bin_align_len
+
g_wim_data
.
new_meta_align_len
+
g_wim_data
.
new_lookup_align_len
;
debug
(
"ventoy_windows_fill_override_data_iso9660 %lu
\n
"
,
(
ulong
)
isosize
);
if
(
g_wim_
d
at
a
.
iso_typ
e
=
=
0
)
for
(
node
=
g_wim_
p
at
ch_head
;
node
;
nod
e
=
node
->
next
)
{
ventoy_iso9660_override
*
dirent
=
(
ventoy_iso9660_override
*
)
g_wim_data
.
override_data
;
wim_data
=
&
node
->
wim_data
;
if
(
0
==
node
->
valid
)
{
continue
;
}
new_wim_size
=
wim_data
->
wim_align_size
+
wim_data
->
bin_align_len
+
wim_data
->
new_meta_align_len
+
wim_data
->
new_lookup_align_len
;
dirent
=
(
ventoy_iso9660_override
*
)
wim_data
->
override_data
;
dirent
->
first_sector
=
(
grub_uint32_t
)
sector
;
dirent
->
size
=
new_wim_size
;
dirent
->
first_sector_be
=
grub_swap_bytes32
(
dirent
->
first_sector
);
dirent
->
size_be
=
grub_swap_bytes32
(
dirent
->
size
);
sector
+=
(
new_wim_size
/
2048
);
/* override 1: position and length in dirent */
cur
->
img_offset
=
wim_data
->
override_offset
;
cur
->
override_size
=
wim_data
->
override_len
;
grub_memcpy
(
cur
->
override_data
,
wim_data
->
override_data
,
cur
->
override_size
);
cur
++
;
/* override 2: new wim file header */
cur
->
img_offset
=
wim_data
->
file_offset
;
cur
->
override_size
=
sizeof
(
wim_header
);
grub_memcpy
(
cur
->
override_data
,
&
(
wim_data
->
wim_header
),
cur
->
override_size
);
cur
++
;
}
else
return
;
}
static
void
ventoy_windows_fill_override_data_udf
(
grub_uint64_t
isosize
,
void
*
override
)
{
grub_uint32_t
data32
;
grub_uint64_t
data64
;
grub_uint64_t
sector
;
grub_uint32_t
new_wim_size
;
grub_uint64_t
total_wim_size
=
0
;
grub_uint32_t
udf_start_block
=
0
;
ventoy_override_chunk
*
cur
;
wim_patch
*
node
=
NULL
;
wim_tail
*
wim_data
=
NULL
;
ventoy_udf_override
*
udf
=
NULL
;
sector
=
(
isosize
+
2047
)
/
2048
;
cur
=
(
ventoy_override_chunk
*
)
override
;
debug
(
"ventoy_windows_fill_override_data_udf %lu
\n
"
,
(
ulong
)
isosize
);
for
(
node
=
g_wim_patch_head
;
node
;
node
=
node
->
next
)
{
ventoy_udf_override
*
udf
=
(
ventoy_udf_override
*
)
g_wim_data
.
override_data
;
udf
->
length
=
new_wim_size
;
udf
->
position
=
(
grub_uint32_t
)
sector
-
g_wim_data
.
udf_start_block
;
wim_data
=
&
node
->
wim_data
;
if
(
node
->
valid
)
{
if
(
udf_start_block
==
0
)
{
udf_start_block
=
wim_data
->
udf_start_block
;
}
new_wim_size
=
wim_data
->
wim_align_size
+
wim_data
->
bin_align_len
+
wim_data
->
new_meta_align_len
+
wim_data
->
new_lookup_align_len
;
total_wim_size
+=
new_wim_size
;
}
}
//override 1: sector number in pd data
cur
->
img_offset
=
grub_udf_get_last_pd_size_offset
();
cur
->
override_size
=
4
;
data32
=
sector
-
g_wim_data
.
udf_start_block
+
(
new
_wim_size
/
2048
);
data32
=
sector
-
udf_start_block
+
(
total
_wim_size
/
2048
);
grub_memcpy
(
cur
->
override_data
,
&
(
data32
),
4
);
//override 2: filesize in file_entry
cur
++
;
cur
->
img_offset
=
g_wim_data
.
fe_entry_size_offset
;
cur
->
override_size
=
8
;
data64
=
new_wim_size
;
grub_memcpy
(
cur
->
override_data
,
&
(
data64
),
8
);
/* override 3: position and length in extend data */
cur
++
;
cur
->
img_offset
=
g_wim_data
.
override_offset
;
cur
->
override_size
=
g_wim_data
.
override_len
;
grub_memcpy
(
cur
->
override_data
,
g_wim_data
.
override_data
,
cur
->
override_size
);
/* override 4: new wim file header */
cur
++
;
cur
->
img_offset
=
g_wim_data
.
file_offset
;
cur
->
override_size
=
sizeof
(
wim_header
);
grub_memcpy
(
cur
->
override_data
,
&
(
g_wim_data
.
wim_header
),
cur
->
override_size
);
for
(
node
=
g_wim_patch_head
;
node
;
node
=
node
->
next
)
{
wim_data
=
&
node
->
wim_data
;
if
(
0
==
node
->
valid
)
{
continue
;
}
new_wim_size
=
wim_data
->
wim_align_size
+
wim_data
->
bin_align_len
+
wim_data
->
new_meta_align_len
+
wim_data
->
new_lookup_align_len
;
//override 2: filesize in file_entry
cur
++
;
cur
->
img_offset
=
wim_data
->
fe_entry_size_offset
;
cur
->
override_size
=
8
;
data64
=
new_wim_size
;
grub_memcpy
(
cur
->
override_data
,
&
(
data64
),
8
);
udf
=
(
ventoy_udf_override
*
)
wim_data
->
override_data
;
udf
->
length
=
new_wim_size
;
udf
->
position
=
(
grub_uint32_t
)
sector
-
udf_start_block
;
sector
+=
(
new_wim_size
/
2048
);
/* override 3: position and length in extend data */
cur
++
;
cur
->
img_offset
=
wim_data
->
override_offset
;
cur
->
override_size
=
wim_data
->
override_len
;
grub_memcpy
(
cur
->
override_data
,
wim_data
->
override_data
,
cur
->
override_size
);
/* override 4: new wim file header */
cur
++
;
cur
->
img_offset
=
wim_data
->
file_offset
;
cur
->
override_size
=
sizeof
(
wim_header
);
grub_memcpy
(
cur
->
override_data
,
&
(
wim_data
->
wim_header
),
cur
->
override_size
);
}
return
;
}
static
grub_uint32_t
ventoy_windows_get_virt_data_size
(
void
)
{
grub_uint32_t
size
=
0
;
wim_tail
*
wim_data
=
NULL
;
wim_patch
*
node
=
g_wim_patch_head
;
while
(
node
)
{
if
(
node
->
valid
)
{
wim_data
=
&
node
->
wim_data
;
size
+=
sizeof
(
ventoy_virt_chunk
)
+
wim_data
->
bin_align_len
+
wim_data
->
new_meta_align_len
+
wim_data
->
new_lookup_align_len
;
}
node
=
node
->
next
;
}
return
size
;
}
static
void
ventoy_windows_fill_virt_data
(
grub_uint64_t
isosize
,
ventoy_chain_head
*
chain
)
{
grub_uint64_t
sector
;
...
...
@@ -732,37 +1104,53 @@ static void ventoy_windows_fill_virt_data( grub_uint64_t isosize, ventoy_chai
grub_uint32_t
mem_secs
;
char
*
override
=
NULL
;
ventoy_virt_chunk
*
cur
=
NULL
;
wim_tail
*
wim_data
=
NULL
;
wim_patch
*
node
=
NULL
;
sector
=
(
isosize
+
2047
)
/
2048
;
offset
=
sizeof
(
ventoy_virt_chunk
);
wim_secs
=
g_wim_data
.
wim_align_size
/
2048
;
mem_secs
=
(
g_wim_data
.
bin_align_len
+
g_wim_data
.
new_meta_align_len
+
g_wim_data
.
new_lookup_align_len
)
/
2048
;
offset
=
sizeof
(
ventoy_virt_chunk
)
*
g_wim_valid_patch_count
;
override
=
(
char
*
)
chain
+
chain
->
virt_chunk_offset
;
cur
=
(
ventoy_virt_chunk
*
)
override
;
cur
->
remap_sector_start
=
sector
;
cur
->
remap_sector_end
=
cur
->
remap_sector_start
+
wim_secs
;
cur
->
org_sector_start
=
(
grub_uint32_t
)(
g_wim_data
.
file_offset
/
2048
);
cur
->
mem_sector_start
=
cur
->
remap_sector_end
;
cur
->
mem_sector_end
=
cur
->
mem_sector_start
+
mem_secs
;
cur
->
mem_sector_offset
=
offset
;
for
(
node
=
g_wim_patch_head
;
node
;
node
=
node
->
next
)
{
if
(
0
==
node
->
valid
)
{
continue
;
}
grub_memcpy
(
override
+
offset
,
g_wim_data
.
jump_bin_data
,
g_wim_data
.
bin_raw_len
);
offset
+=
g_wim_data
.
bin_align_len
;
wim_data
=
&
node
->
wim_data
;
grub_memcpy
(
override
+
offset
,
g_wim_data
.
new_meta_data
,
g_wim_data
.
new_meta_len
);
offset
+=
g_wim_data
.
new_meta_align_len
;
grub_memcpy
(
override
+
offset
,
g_wim_data
.
new_lookup_data
,
g_wim_data
.
new_lookup_len
);
offset
+=
g_wim_data
.
new_lookup_align_len
;
wim_secs
=
wim_data
->
wim_align_size
/
2048
;
mem_secs
=
(
wim_data
->
bin_align_len
+
wim_data
->
new_meta_align_len
+
wim_data
->
new_lookup_align_len
)
/
2048
;
cur
->
remap_sector_start
=
sector
;
cur
->
remap_sector_end
=
cur
->
remap_sector_start
+
wim_secs
;
cur
->
org_sector_start
=
(
grub_uint32_t
)(
wim_data
->
file_offset
/
2048
);
cur
->
mem_sector_start
=
cur
->
remap_sector_end
;
cur
->
mem_sector_end
=
cur
->
mem_sector_start
+
mem_secs
;
cur
->
mem_sector_offset
=
offset
;
sector
+=
wim_secs
+
mem_secs
;
cur
++
;
grub_memcpy
(
override
+
offset
,
wim_data
->
jump_bin_data
,
wim_data
->
bin_raw_len
);
offset
+=
wim_data
->
bin_align_len
;
grub_memcpy
(
override
+
offset
,
wim_data
->
new_meta_data
,
wim_data
->
new_meta_len
);
offset
+=
wim_data
->
new_meta_align_len
;
grub_memcpy
(
override
+
offset
,
wim_data
->
new_lookup_data
,
wim_data
->
new_lookup_len
);
offset
+=
wim_data
->
new_lookup_align_len
;
chain
->
virt_img_size_in_bytes
+=
wim_data
->
wim_align_size
+
wim_data
->
bin_align_len
+
wim_data
->
new_meta_align_len
+
wim_data
->
new_lookup_align_len
;
}
chain
->
virt_img_size_in_bytes
+=
g_wim_data
.
wim_align_size
+
g_wim_data
.
bin_align_len
+
g_wim_data
.
new_meta_align_len
+
g_wim_data
.
new_lookup_align_len
;
return
;
}
...
...
@@ -828,7 +1216,7 @@ grub_err_t ventoy_cmd_windows_chain_data(grub_extcmd_context_t ctxt, int argc, c
return
1
;
}
if
(
0
==
ventoy_compatible
&&
g_wim_
data
.
new_meta_data
==
NULL
)
if
(
0
==
ventoy_compatible
&&
g_wim_
valid_patch_count
==
0
)
{
unknown_image
=
1
;
debug
(
"Warning: %s was not recognized by Ventoy
\n
"
,
args
[
0
]);
...
...
@@ -871,8 +1259,7 @@ grub_err_t ventoy_cmd_windows_chain_data(grub_extcmd_context_t ctxt, int argc, c
else
{
override_size
=
ventoy_get_override_chunk_num
()
*
sizeof
(
ventoy_override_chunk
);
virt_chunk_size
=
sizeof
(
ventoy_virt_chunk
)
+
g_wim_data
.
bin_align_len
+
g_wim_data
.
new_meta_align_len
+
g_wim_data
.
new_lookup_align_len
;;
virt_chunk_size
=
ventoy_windows_get_virt_data_size
();
size
=
sizeof
(
ventoy_chain_head
)
+
img_chunk_size
+
override_size
+
virt_chunk_size
;
}
...
...
@@ -903,9 +1290,10 @@ grub_err_t ventoy_cmd_windows_chain_data(grub_extcmd_context_t ctxt, int argc, c
grub_memset
(
chain
,
0
,
sizeof
(
ventoy_chain_head
));
/* part 1: os parameter */
g_ventoy_chain_type
=
1
;
ventoy_fill_os_param
(
file
,
&
(
chain
->
os_param
));
if
(
g_wim_data
.
jump_bin_data
&&
g_wim_data
.
new_meta_data
)
if
(
0
==
unknown_image
)
{
ventoy_update_before_chain
(
&
(
chain
->
os_param
),
args
[
0
]);
}
...
...
@@ -934,7 +1322,7 @@ grub_err_t ventoy_cmd_windows_chain_data(grub_extcmd_context_t ctxt, int argc, c
return
0
;
}
if
(
g_wim_
data
.
new_meta_data
==
NULL
)
if
(
0
==
g_wim_
valid_patch_count
)
{
return
0
;
}
...
...
@@ -942,11 +1330,19 @@ grub_err_t ventoy_cmd_windows_chain_data(grub_extcmd_context_t ctxt, int argc, c
/* part 4: override chunk */
chain
->
override_chunk_offset
=
chain
->
img_chunk_offset
+
img_chunk_size
;
chain
->
override_chunk_num
=
ventoy_get_override_chunk_num
();
ventoy_windows_fill_override_data
(
isosize
,
(
char
*
)
chain
+
chain
->
override_chunk_offset
);
if
(
g_iso_fs_type
==
0
)
{
ventoy_windows_fill_override_data_iso9660
(
isosize
,
(
char
*
)
chain
+
chain
->
override_chunk_offset
);
}
else
{
ventoy_windows_fill_override_data_udf
(
isosize
,
(
char
*
)
chain
+
chain
->
override_chunk_offset
);
}
/* part 5: virt chunk */
chain
->
virt_chunk_offset
=
chain
->
override_chunk_offset
+
override_size
;
chain
->
virt_chunk_num
=
1
;
chain
->
virt_chunk_num
=
g_wim_valid_patch_count
;
ventoy_windows_fill_virt_data
(
isosize
,
chain
);
if
(
ventoy_is_efi_os
()
==
0
)
...
...
@@ -1099,6 +1495,7 @@ grub_err_t ventoy_cmd_wim_chain_data(grub_extcmd_context_t ctxt, int argc, char
grub_memset
(
chain
,
0
,
sizeof
(
ventoy_chain_head
));
/* part 1: os parameter */
g_ventoy_chain_type
=
0
;
ventoy_fill_os_param
(
file
,
&
(
chain
->
os_param
));
/* part 2: chain head */
...
...
GRUB2/MOD_SRC/grub-2.04/include/grub/file.h
0 → 100644
View file @
a5c70651
/*
* GRUB -- GRand Unified Bootloader
* Copyright (C) 2002,2007 Free Software Foundation, Inc.
*
* GRUB is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* GRUB is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with GRUB. If not, see <http://www.gnu.org/licenses/>.
*/
#ifndef GRUB_FILE_HEADER
#define GRUB_FILE_HEADER 1
#include <grub/types.h>
#include <grub/err.h>
#include <grub/device.h>
#include <grub/fs.h>
#include <grub/disk.h>
enum
grub_file_type
{
GRUB_FILE_TYPE_NONE
=
0
,
/* GRUB module to be loaded. */
GRUB_FILE_TYPE_GRUB_MODULE
,
/* Loopback file to be represented as disk. */
GRUB_FILE_TYPE_LOOPBACK
,
/* Linux kernel to be loaded. */
GRUB_FILE_TYPE_LINUX_KERNEL
,
/* Linux initrd. */
GRUB_FILE_TYPE_LINUX_INITRD
,
/* Multiboot kernel. */
GRUB_FILE_TYPE_MULTIBOOT_KERNEL
,
/* Multiboot module. */
GRUB_FILE_TYPE_MULTIBOOT_MODULE
,
/* Xen hypervisor - used on ARM only. */
GRUB_FILE_TYPE_XEN_HYPERVISOR
,
/* Xen module - used on ARM only. */
GRUB_FILE_TYPE_XEN_MODULE
,
GRUB_FILE_TYPE_BSD_KERNEL
,
GRUB_FILE_TYPE_FREEBSD_ENV
,
GRUB_FILE_TYPE_FREEBSD_MODULE
,
GRUB_FILE_TYPE_FREEBSD_MODULE_ELF
,
GRUB_FILE_TYPE_NETBSD_MODULE
,
GRUB_FILE_TYPE_OPENBSD_RAMDISK
,
GRUB_FILE_TYPE_XNU_INFO_PLIST
,
GRUB_FILE_TYPE_XNU_MKEXT
,
GRUB_FILE_TYPE_XNU_KEXT
,
GRUB_FILE_TYPE_XNU_KERNEL
,
GRUB_FILE_TYPE_XNU_RAMDISK
,
GRUB_FILE_TYPE_XNU_HIBERNATE_IMAGE
,
GRUB_FILE_XNU_DEVPROP
,
GRUB_FILE_TYPE_PLAN9_KERNEL
,
GRUB_FILE_TYPE_NTLDR
,
GRUB_FILE_TYPE_TRUECRYPT
,
GRUB_FILE_TYPE_FREEDOS
,
GRUB_FILE_TYPE_PXECHAINLOADER
,
GRUB_FILE_TYPE_PCCHAINLOADER
,
GRUB_FILE_TYPE_COREBOOT_CHAINLOADER
,
GRUB_FILE_TYPE_EFI_CHAINLOADED_IMAGE
,
/* File holding signature. */
GRUB_FILE_TYPE_SIGNATURE
,
/* File holding public key to verify signature once. */
GRUB_FILE_TYPE_PUBLIC_KEY
,
/* File holding public key to add to trused keys. */
GRUB_FILE_TYPE_PUBLIC_KEY_TRUST
,
/* File of which we intend to print a blocklist to the user. */
GRUB_FILE_TYPE_PRINT_BLOCKLIST
,
/* File we intend to use for test loading or testing speed. */
GRUB_FILE_TYPE_TESTLOAD
,
/* File we open only to get its size. E.g. in ls output. */
GRUB_FILE_TYPE_GET_SIZE
,
/* Font file. */
GRUB_FILE_TYPE_FONT
,
/* File holding encryption key for encrypted ZFS. */
GRUB_FILE_TYPE_ZFS_ENCRYPTION_KEY
,
/* File we open n grub-fstest. */
GRUB_FILE_TYPE_FSTEST
,
/* File we open n grub-mount. */
GRUB_FILE_TYPE_MOUNT
,
/* File which we attempt to identify the type of. */
GRUB_FILE_TYPE_FILE_ID
,
/* File holding ACPI table. */
GRUB_FILE_TYPE_ACPI_TABLE
,
/* File holding Device Tree. */
GRUB_FILE_TYPE_DEVICE_TREE_IMAGE
,
/* File we intend show to user. */
GRUB_FILE_TYPE_CAT
,
GRUB_FILE_TYPE_HEXCAT
,
/* One of pair of files we intend to compare. */
GRUB_FILE_TYPE_CMP
,
/* List of hashes for hashsum. */
GRUB_FILE_TYPE_HASHLIST
,
/* File hashed by hashsum. */
GRUB_FILE_TYPE_TO_HASH
,
/* Keyboard layout. */
GRUB_FILE_TYPE_KEYBOARD_LAYOUT
,
/* Picture file. */
GRUB_FILE_TYPE_PIXMAP
,
/* *.lst shipped by GRUB. */
GRUB_FILE_TYPE_GRUB_MODULE_LIST
,
/* config file. */
GRUB_FILE_TYPE_CONFIG
,
GRUB_FILE_TYPE_THEME
,
GRUB_FILE_TYPE_GETTEXT_CATALOG
,
GRUB_FILE_TYPE_FS_SEARCH
,
GRUB_FILE_TYPE_AUDIO
,
GRUB_FILE_TYPE_VBE_DUMP
,
GRUB_FILE_TYPE_LOADENV
,
GRUB_FILE_TYPE_SAVEENV
,
GRUB_FILE_TYPE_VERIFY_SIGNATURE
,
GRUB_FILE_TYPE_MASK
=
0xffff
,
/* --skip-sig is specified. */
GRUB_FILE_TYPE_SKIP_SIGNATURE
=
0x10000
,
GRUB_FILE_TYPE_NO_DECOMPRESS
=
0x20000
};
/* File description. */
struct
grub_file
{
/* File name. */
char
*
name
;
/* The underlying device. */
grub_device_t
device
;
/* The underlying filesystem. */
grub_fs_t
fs
;
/* The current offset. */
grub_off_t
offset
;
grub_off_t
progress_offset
;
/* Progress info. */
grub_uint64_t
last_progress_time
;
grub_off_t
last_progress_offset
;
grub_uint64_t
estimated_speed
;
/* The file size. */
grub_off_t
size
;
/* If file is not easily seekable. Should be set by underlying layer. */
int
not_easily_seekable
;
/* Filesystem-specific data. */
void
*
data
;
/* This is called when a sector is read. Used only for a disk device. */
grub_disk_read_hook_t
read_hook
;
/* Caller-specific data passed to the read hook. */
void
*
read_hook_data
;
};
typedef
struct
grub_file
*
grub_file_t
;
extern
grub_disk_read_hook_t
EXPORT_VAR
(
grub_file_progress_hook
);
/* Filters with lower ID are executed first. */
typedef
enum
grub_file_filter_id
{
GRUB_FILE_FILTER_VERIFY
,
GRUB_FILE_FILTER_GZIO
,
GRUB_FILE_FILTER_XZIO
,
GRUB_FILE_FILTER_LZOPIO
,
GRUB_FILE_FILTER_MAX
,
GRUB_FILE_FILTER_COMPRESSION_FIRST
=
GRUB_FILE_FILTER_GZIO
,
GRUB_FILE_FILTER_COMPRESSION_LAST
=
GRUB_FILE_FILTER_LZOPIO
,
}
grub_file_filter_id_t
;
typedef
grub_file_t
(
*
grub_file_filter_t
)
(
grub_file_t
in
,
enum
grub_file_type
type
);
extern
grub_file_filter_t
EXPORT_VAR
(
grub_file_filters
)[
GRUB_FILE_FILTER_MAX
];
static
inline
void
grub_file_filter_register
(
grub_file_filter_id_t
id
,
grub_file_filter_t
filter
)
{
grub_file_filters
[
id
]
=
filter
;
}
static
inline
void
grub_file_filter_unregister
(
grub_file_filter_id_t
id
)
{
grub_file_filters
[
id
]
=
0
;
}
/* Get a device name from NAME. */
char
*
EXPORT_FUNC
(
grub_file_get_device_name
)
(
const
char
*
name
);
int
EXPORT_FUNC
(
ventoy_check_file_exist
)
(
const
char
*
fmt
,
...);
grub_file_t
EXPORT_FUNC
(
grub_file_open
)
(
const
char
*
name
,
enum
grub_file_type
type
);
grub_ssize_t
EXPORT_FUNC
(
grub_file_read
)
(
grub_file_t
file
,
void
*
buf
,
grub_size_t
len
);
grub_off_t
EXPORT_FUNC
(
grub_file_seek
)
(
grub_file_t
file
,
grub_off_t
offset
);
grub_err_t
EXPORT_FUNC
(
grub_file_close
)
(
grub_file_t
file
);
/* Return value of grub_file_size() in case file size is unknown. */
#define GRUB_FILE_SIZE_UNKNOWN 0xffffffffffffffffULL
static
inline
grub_off_t
grub_file_size
(
const
grub_file_t
file
)
{
return
file
->
size
;
}
static
inline
grub_off_t
grub_file_tell
(
const
grub_file_t
file
)
{
return
file
->
offset
;
}
static
inline
int
grub_file_seekable
(
const
grub_file_t
file
)
{
return
!
file
->
not_easily_seekable
;
}
grub_file_t
grub_file_offset_open
(
grub_file_t
parent
,
enum
grub_file_type
type
,
grub_off_t
start
,
grub_off_t
size
);
void
grub_file_offset_close
(
grub_file_t
file
);
#endif
/* ! GRUB_FILE_HEADER */
GRUB2/MOD_SRC/grub-2.04/include/grub/ventoy.h
View file @
a5c70651
...
...
@@ -109,6 +109,8 @@ typedef struct ventoy_os_param
*
* vtoy_reserved[0]: vtoy_break_level
* vtoy_reserved[1]: vtoy_debug_level
* vtoy_reserved[2]: vtoy_chain_type 0:Linux 1:Windows
* vtoy_reserved[3]: vtoy_iso_format 0:iso9660 1:udf
*
*/
grub_uint8_t
vtoy_reserved
[
32
];
// Internal use by ventoy
...
...
@@ -227,6 +229,7 @@ typedef struct ventoy_grub_param
int
grub_ext_get_file_chunk
(
grub_uint64_t
part_start
,
grub_file_t
file
,
ventoy_img_chunk_list
*
chunk_list
);
int
grub_fat_get_file_chunk
(
grub_uint64_t
part_start
,
grub_file_t
file
,
ventoy_img_chunk_list
*
chunk_list
);
void
grub_iso9660_set_nojoliet
(
int
nojoliet
);
grub_uint64_t
grub_iso9660_get_last_read_pos
(
grub_file_t
file
);
grub_uint64_t
grub_iso9660_get_last_file_dirent_pos
(
grub_file_t
file
);
grub_uint64_t
grub_udf_get_file_offset
(
grub_file_t
file
);
...
...
Prev
1
2
3
Next
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
.
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment