神雕大侠写的Syslinux4USB是我在无忧论坛里找到的工具,他是2011年写出的,他在帖子里也发布了源码,可惜那个帖子里的链接失效了,我为了这个工具的源码找了2年,终于在Google上搜到了,并且修改了其中的代码,扩展了它的功能。
神雕的Syslinux4USB用的是syslinux 4.03的版本做的,syslinux 4.03版是2010年发布的,所以算是比较老的版本了,可能对新的硬件不太支持,所以我依次制作了Syslinux4USB 0.2和Syslinux4USB 0.3版本,分别采用syslinux 4.06和syslinux 6.02制作。增加了HDT(Hardware Detection Tool,硬件侦测工具)等一些功能,增加的功能都是从Grml Linux发行版的LiveCD中模仿来的。
从代码全局来看,主要分为版本模块、界面模块、语言模块、逻辑流程模块、U盘引导模块、文件部署模块等6个部分,我们仅仅需要改的是第一部分和最后一部分,也就是修改一下版本和要复制的文件就可以了。
首先,从定义的宏VERSION可以看出,这是用来定义版本的,如果你想修改程序名称和版本号,可以修改宏NAME和VERSION的内容。
然后下面就是修改复制的文件的部分,主要是修改File后的文件路径和名称,Copyfiles后面的文件路径和File后的文件路径对应,而后面的”$BootDir……”内容是用来指定syslinux所有文件放到U盘中的路径,必须逐个指定,File也需要逐个指定。
由于对NSIS的语法不了解,所以这篇文章只做分享,不做分析,有兴趣的可以翻译NSIS的手册。
最后,恐怕连神雕本人都想不到这个工具还会有后续版本,本文也算是对前辈的精神的回赠。
下面是Syslinux4USB 0.3的源代码:
!define NAME "Syslinux4USB"
!define DISTRO "Boot Files"
!define FILENAME "Syslinux4USB"
!define VERSION "v0.3"
!define MUI_ICON "syslinux4usb.ico"
RequestExecutionLevel highest
SetCompressor LZMA
CRCCheck On
XPStyle on
ShowInstDetails show
BrandingText "USB启动界面美化最佳方案 神雕teasiu作品"
CompletedText "启动安装完成,您的USB盘现在已经准备好启动了!"
InstallButtonText "创建"
Name "${NAME} ${VERSION}"
OutFile "${FILENAME}.exe"
!include "MUI2.nsh"
!include "FileFunc.nsh"
; Interface settings
!define MUI_FINISHPAGE_NOAUTOCLOSE
!define MUI_HEADERIMAGE
!define MUI_HEADERIMAGE_BITMAP "usb-logo-nsis.bmp"
!define MUI_HEADERIMAGE_BITMAP_NOSTRETCH
!define MUI_HEADERIMAGE_RIGHT
; License page
!define MUI_TEXT_LICENSE_SUBTITLE $(License_Subtitle)
!define MUI_LICENSEPAGE_TEXT_TOP $(License_Text_Top)
!define MUI_LICENSEPAGE_TEXT_BOTTOM $(License_Text_Bottom)
!insertmacro MUI_PAGE_LICENSE "license.txt"
; Drive page
Var DestDriveTxt
Var DestDrive
Var DestDisk
Var LabelDrivePageText
Var LabelDriveSelect
Var Format
Var FormatMe
Var Warning
Page custom drivePage
; Instfiles page
!define MUI_INSTFILESPAGE_COLORS "00FF00 000000" ;Green and Black
!define MUI_TEXT_INSTALLING_TITLE $(Install_Title)
!define MUI_TEXT_INSTALLING_SUBTITLE $(Install_SubTitle)
!define MUI_TEXT_FINISH_SUBTITLE $(Install_Finish_Sucess)
!insertmacro MUI_PAGE_INSTFILES
; Finish page
!define MUI_FINISHPAGE_TITLE $(Finish_Title)
!define MUI_FINISHPAGE_TEXT $(Finish_Text)
!define MUI_FINISHPAGE_LINK $(Finish_Link)
!define MUI_FINISHPAGE_LINK_LOCATION "http://bbs.wuyou.net/"
!insertmacro MUI_PAGE_FINISH
; Language files
!insertmacro MUI_LANGUAGE "English" ;first language is the default language
!insertmacro MUI_LANGUAGE "SimpChinese"
; English
LangString License_Subtitle ${LANG_ENGLISH} "Please review the license terms before running ${NAME}."
LangString License_Text_Top ${LANG_ENGLISH} "The software within this program falls under the following License."
LangString License_Text_Bottom ${LANG_ENGLISH} "You must accept the terms of this License agreement to run ${NAME}. If you agree, Click I Agree to Continue."
LangString Finish_Title ${LANG_ENGLISH} "${NAME} has completed the installation."
LangString Finish_Text ${LANG_ENGLISH} "The necessary files are installed on your USB drive and the drive is bootable.$\r$\n$\r$\nNow you should proceed to see if it boots"
LangString Finish_Link ${LANG_ENGLISH} "Visit the Official Memtest86+ Site"
LangString DrivePage_Title ${LANG_ENGLISH} "Choose USB drive location"
LangString DrivePage_Title2 ${LANG_ENGLISH} "Choose the USB drive in which to make bootable."
LangString DrivePage_Text ${LANG_ENGLISH} "Please select your USB Flash Drive and Format option. ${NAME} will proceed to make this drive Bootable and install the Memtest86+ tool on it."
LangString DrivePage_Input ${LANG_ENGLISH} "Select your USB Flash Drive"
LangString WarningPage_Text ${LANG_ENGLISH} "WARNING!! Contents on this Drive will be deleted. Any exisiting MBR WILL be overwritten. Make sure you have backed up any important content!$\r$\n$\r$\nWhen you are sure, click Create to proceed."
LangString Syslinux_Creation ${LANG_ENGLISH} "Create syslinux configuration and moving files to $DestDrive "
LangString Syslinux_Execution ${LANG_ENGLISH} "Execute syslinux on $R0"
LangString Syslinux_Warning ${LANG_ENGLISH} "An error ($R8) occurred while executing syslinux.$\r$\nYour USB drive won't be bootable..."
LangString Install_Title ${LANG_ENGLISH} "Installing ${DISTRO}"
LangString Install_SubTitle ${LANG_ENGLISH} "Please wait while ${NAME} installs ${DISTRO} on $0"
LangString Install_Finish_Sucess ${LANG_ENGLISH} "${NAME} sucessfully installed ${DISTRO} on $0"
LangString License_Subtitle ${LANG_SIMPCHINESE} "创建USB启动之前请认真阅读本协议 ${NAME}."
LangString License_Text_Top ${LANG_SIMPCHINESE} "本程序的软件属于下面的许可."
LangString License_Text_Bottom ${LANG_SIMPCHINESE} "您必须接受以下许可协议来运行 ${NAME}.$\r$\n$\r$\n 如果你同意,请按 我接受 然后继续."
LangString Finish_Title ${LANG_SIMPCHINESE} "${NAME} 已经完成启动创建."
LangString Finish_Text ${LANG_SIMPCHINESE} "必要的文件已安装在您的USB驱动器并且可启动.$\r$\n$\r$\n现在您可以启动它并进行引导了."
LangString Finish_Link ${LANG_SIMPCHINESE} "访问本启动器作者的官方网站"
LangString DrivePage_Title ${LANG_SIMPCHINESE} "选择USB驱动器的位置"
LangString DrivePage_Title2 ${LANG_SIMPCHINESE} "在框中选择您想让它可启动的USB驱动器."
LangString DrivePage_Text ${LANG_SIMPCHINESE} "请选择您的USB闪存驱动器和格式选项. ${NAME}使该驱动器可启动并进行引导."
LangString DrivePage_Input ${LANG_SIMPCHINESE} "选择您的USB闪存驱动器"
LangString WarningPage_Text ${LANG_SIMPCHINESE} "警告!此驱动器的内容将被删除. 任何现有的MBR将被覆盖. 请确认您的重要内容已经备份!$\r$\n$\r$\n如果您确认完毕, 点击创建按钮."
LangString Syslinux_Creation ${LANG_SIMPCHINESE} "创建syslinux的配置和移动文件到$DestDrive"
LangString Syslinux_Execution ${LANG_SIMPCHINESE} "执行syslinux到 $R0"
LangString Syslinux_Warning ${LANG_SIMPCHINESE} "一个错误 ($R8) 发生在当执行syslinux时.$\r$\n您的USB驱动器将不可启动.."
LangString Install_Title ${LANG_SIMPCHINESE} "安装中 ${DISTRO}"
LangString Install_SubTitle ${LANG_SIMPCHINESE} "请稍后 ${NAME} 安装 ${DISTRO} 到 $0"
LangString Install_Finish_Sucess ${LANG_SIMPCHINESE} "${NAME} 已经成功安装了 ${DISTRO} 到 $0"
Function drivePage
!insertmacro MUI_HEADER_TEXT $(DrivePage_Title) $(DrivePage_Title2)
nsDialogs::Create
${If} $DestDrive == ""
GetDlgItem $ $HWNDPARENT ; Get next control handle
EnableWindow $ ; disable next
${EndIf}
${NSD_CreateLabel} % $(DrivePage_Text)
Pop $LabelDrivePageText
${NSD_CreateLabel} % $(DrivePage_Input)
Pop $LabelDriveSelect
${NSD_CreateDroplist} % ""
Pop $DestDriveTxt
${NSD_OnChange} $DestDriveTxt db_select.onchange
${GetDrives} "FDD" driveList
${If} $DestDrive != ""
${NSD_CB_SelectString} $DestDriveTxt $DestDrive
${EndIf}
; Format Drive Option
${NSD_CreateCheckBox} % % "如果你想格式化USB驱动器,选中此复选框."
Pop $Format
${NSD_OnClick} $Format FormatIt
; Warning Label
${NSD_CreateLabel} % $(WarningPage_Text)
Pop $Warning
EnableWindow $Format
ShowWindow $Warning
GetDlgItem $ $HWNDPARENT
ShowWindow $ ; Disable Back
nsDialogs::Show
FunctionEnd
Function db_select.onchange
Pop $DestDriveTxt
${NSD_GetText} $DestDriveTxt $
StrCpy $DestDrive "$0"
StrCpy $DestDisk $DestDrive -
GetDlgItem $ $HWNDPARENT ; Get "Next" control handle
EnableWindow $ ; enable "Next" control
EnableWindow $Format
ShowWindow $Warning
SetCtlColors $Warning /Branding FF0000
Call FormatIt
FunctionEnd
Function driveList
SendMessage $DestDriveTxt ${CB_ADDSTRING} "STR:$9"
Push
FunctionEnd
Function FormatIt ; Set Format Option
${NSD_GetState} $Format $FormatMe
${If} $FormatMe == ${BST_CHECKED}
${NSD_Check} $Format
StrCpy $FormatMe "Yes"
${NSD_SetText} $Format "我们将格式化 $DestDrive 为 Fat32."
${ElseIf} $FormatMe == ${BST_UNCHECKED}
${NSD_Uncheck} $Format
${NSD_SetText} $Format "(推荐)如果你想格式化USB驱动器,选中此复选框 $DestDrive"
${EndIf}
FunctionEnd
Function FormatYes ; If Format is checked, do something
${If} $FormatMe == "Yes"
DetailPrint "正在格式化 $DestDisk"
InitPluginsDir
File /oname=$PLUGINSDIR\fbinst.exe "fbinst.exe"
# nsExec::ExecToLog '"cmd" /c "format $DestDisk /FS:Fat32 /V:JHJHORG /Q /y"'
nsExec::ExecToLog '"cmd" /c "echo y|$PLUGINSDIR\fbinst $DestDisk format --raw --force --fat32"'
${EndIf}
FunctionEnd
Section "Copyfiles" main
Call FormatYes ; Format the Drive?
InitPluginsDir
File /oname=$PLUGINSDIR\syslinux.exe "syslinux.exe"
File /oname=$PLUGINSDIR\syslinux.cfg "syslinux.cfg"
File /oname=$PLUGINSDIR\Readme.txt "Readme.txt"
File /oname=$PLUGINSDIR\back.jpg "back.jpg"
File /oname=$PLUGINSDIR\balder10.imz "balder10.imz"
File /oname=$PLUGINSDIR\chain.c32 "chain.c32"
File /oname=$PLUGINSDIR\gfxboot.c32 "gfxboot.c32"
File /oname=$PLUGINSDIR\hdt.c32 "hdt.c32"
File /oname=$PLUGINSDIR\ifcpu64.c32 "ifcpu64.c32"
File /oname=$PLUGINSDIR\ipxe.lkrn "ipxe.lkrn"
File /oname=$PLUGINSDIR\libcom32.c32 "libcom32.c32"
File /oname=$PLUGINSDIR\libgpl.c32 "libgpl.c32"
File /oname=$PLUGINSDIR\libmenu.c32 "libmenu.c32"
File /oname=$PLUGINSDIR\libutil.c32 "libutil.c32"
File /oname=$PLUGINSDIR\mboot.c32 "mboot.c32"
File /oname=$PLUGINSDIR\memdisk "memdisk"
File /oname=$PLUGINSDIR\menu.c32 "menu.c32"
File /oname=$PLUGINSDIR\pci.ids "pci.ids"
File /oname=$PLUGINSDIR\poweroff.c32 "poweroff.c32"
File /oname=$PLUGINSDIR\reboot.c32 "reboot.c32"
File /oname=$PLUGINSDIR\vesamenu.c32 "vesamenu.c32"
SetShellVarContext all
; Execute syslinux on the drive
StrCpy $R0 $DestDrive - ; remove \ for syslinux
ClearErrors
DetailPrint $(Syslinux_Execution)
ExecWait '$PLUGINSDIR\syslinux.exe -maf $R0' $R8
DetailPrint "Return $R8"
Banner::destroy
${If} $R8 !=
MessageBox MB_ICONEXCLAMATION|MB_OK $(Syslinux_Warning)
${EndIf}
; Create files
Var /GLOBAL BootDir
StrCpy $BootDir $DestDrive -
StrCpy $BootDir "$BootDir"
DetailPrint $(Syslinux_Creation)
CreateDirectory $BootDir\boot
CopyFiles "$PLUGINSDIR\syslinux.cfg" "$BootDir\syslinux.cfg" ; move syslinux.cfg
CopyFiles "$PLUGINSDIR\Readme.txt" "$BootDir\Readme.txt" ; move Readme
CopyFiles "$PLUGINSDIR\libcom32.c32" "$BootDir\libcom32.c32"
CopyFiles "$PLUGINSDIR\libgpl.c32" "$BootDir\libgpl.c32"
CopyFiles "$PLUGINSDIR\libmenu.c32" "$BootDir\libmenu.c32"
CopyFiles "$PLUGINSDIR\libutil.c32" "$BootDir\libutil.c32"
CopyFiles "$PLUGINSDIR\back.jpg" "$BootDir\boot\back.jpg"
CopyFiles "$PLUGINSDIR\balder10.imz" "$BootDir\boot\balder10.imz"
CopyFiles "$PLUGINSDIR\chain.c32" "$BootDir\boot\chain.c32"
CopyFiles "$PLUGINSDIR\gfxboot.c32" "$BootDir\boot\gfxboot.c32"
CopyFiles "$PLUGINSDIR\hdt.c32" "$BootDir\boot\hdt.c32"
CopyFiles "$PLUGINSDIR\ifcpu64.c32" "$BootDir\boot\ifcpu64.c32"
CopyFiles "$PLUGINSDIR\ipxe.lkrn" "$BootDir\boot\ipxe.lkrn"
CopyFiles "$PLUGINSDIR\mboot.c32" "$BootDir\boot\mboot.c32"
CopyFiles "$PLUGINSDIR\memdisk" "$BootDir\boot\memdisk"
CopyFiles "$PLUGINSDIR\menu.c32" "$BootDir\boot\menu.c32"
CopyFiles "$PLUGINSDIR\pci.ids" "$BootDir\boot\pci.ids"
CopyFiles "$PLUGINSDIR\poweroff.c32" "$BootDir\boot\poweroff.c32"
CopyFiles "$PLUGINSDIR\reboot.c32" "$BootDir\boot\reboot.c32"
CopyFiles "$PLUGINSDIR\vesamenu.c32" "$BootDir\boot\vesamenu.c32"
SectionEnd