diff --git a/export.ps1 b/export.ps1 index 12b03f71fe..2daa7575aa 100644 --- a/export.ps1 +++ b/export.ps1 @@ -63,7 +63,7 @@ if ($dif_Path -ne $null) { Write-Output "Checking if Python packages are up to date..." -Start-Process -Wait -NoNewWindow -FilePath "python" -Args "$IDF_PATH/tools/check_python_dependencies.py" +Start-Process -Wait -NoNewWindow -FilePath "python" -Args "`"$IDF_PATH/tools/check_python_dependencies.py`"" if ($LASTEXITCODE -ne 0) { exit $LASTEXITCODE } # if error Write-Output " diff --git a/tools/windows/tool_setup/idf_cmd_init.ps1 b/tools/windows/tool_setup/idf_cmd_init.ps1 new file mode 100644 index 0000000000..280f3dc4da --- /dev/null +++ b/tools/windows/tool_setup/idf_cmd_init.ps1 @@ -0,0 +1,108 @@ +# This script is called from a Windows shortcut, with +# the working directory set to an ESP-IDF directory. +# Its purpose is to support using the "IDF Tools Directory" method of +# installation for ESP-IDF versions older than IDF v4.1. +# It does the same thing as "export.ps1" in IDF v4.1. + +Param +( + [String]$IdfGitDir, + [String]$IdfPythonDir +) + +$IDF_PATH = "." +$isEspIdfRoot = (Test-Path "$IDF_PATH/tools/idf.py") +if (-not $isEspIdfRoot) { + Write-Output "Usage: idf_cmd_init.ps1 ^ ^" + Write-Output "This script must be invoked from ESP-IDF directory." +} + +# Strip quotes +$IdfGitDir = $IdfGitDir.Trim("`"") +$IdfPythonDir = $IdfPythonDir.Trim("`"") + +# Add Python and Git paths to PATH +$env:PATH = "$IdfGitDir;$IdfPythonDir;$env:PATH" +Write-Output "Using Python in $IdfPythonDir" +python.exe --version +Write-Output "Using Git in $IdfGitDir" +git.exe --version + +# Check if this is a recent enough copy of ESP-IDF. +# If so, use export.ps1 provided there. +$isExport = (Test-Path "$IDF_PATH/export.ps1") +if ($isExport){ + . $IDF_PATH/export.ps1 +} +else { + Write-Output "IDF version does not include export.ps1. Using the fallback version." + + if ((Test-Path "$IDF_PATH/tools/tools.json")){ + $IDF_TOOLS_JSON_PATH = "$IDF_PATH/tools/tools.json" + } + else{ + Write-Output "IDF version does not include tools/tools.json. Using the fallback version." + $IDF_TOOLS_JSON_PATH = "$PSScriptRoot/tools_fallback.json" + } + + if ((Test-Path "$IDF_PATH/tools/idf_tools.py")){ + $IDF_TOOLS_PY_PATH = "$IDF_PATH/tools/idf_tools.py" + } + else{ + Write-Output "IDF version does not include tools/idf_tools.py. Using the fallback version." + $IDF_TOOLS_PY_PATH = "$PSScriptRoot/idf_tools_fallback.py" + } + + Write-Output "Setting IDF_PATH: $IDF_PATH" + $env:IDF_PATH = $IDF_PATH + + Write-Output "Adding ESP-IDF tools to PATH..." + $OLD_PATH = $env:Path.split(";") | Select-Object -Unique # array without duplicates + # using idf_tools.py to get $envars_array to set + $envars_raw = (python.exe "$IDF_TOOLS_PY_PATH" --tools-json "$IDF_TOOLS_JSON_PATH" export --format key-value) + if ($LASTEXITCODE -ne 0) { exit $LASTEXITCODE } # if error + + $envars_array # will be filled like: + # [ + # [vname1, vval1], [vname2, vval2], ... + # ] + foreach ($line in $envars_raw) { + $pair = $line.split("=") # split in name, val + $var_name = $pair[0].Trim() # trim spaces on the ends of the name + $var_val = $pair[1].Trim() # trim spaces on the ends of the val + $var_val = $var_val -replace "%(.+)%", "`$env:`$1" # convert var syntax to PS using RegEx + $var_val = $ExecutionContext.InvokeCommand.ExpandString($var_val) # expand variables to values + $envars_array += (, ($var_name, $var_val)) + } + + foreach ($pair in $envars_array) { + # setting the values + $var_name = $pair[0].Trim() # trim spaces on the ends of the name + $var_val = $pair[1].Trim() # trim spaces on the ends of the val + Set-Item -Path "Env:$var_name" -Value "$var_val" + } + + #Compare Path's OLD vs. NEW + $NEW_PATH = $env:Path.split(";") | Select-Object -Unique # array without duplicates + $dif_Path = Compare-Object -ReferenceObject $OLD_PATH -DifferenceObject $NEW_PATH -PassThru + if ($dif_Path -ne $null) { + Write-Output $dif_Path + } + else { + Write-Output "No directories added to PATH:" + Write-Output $OLD_PATH + } + + + Write-Output "Checking if Python packages are up to date..." + + Start-Process -Wait -NoNewWindow -FilePath "python" -Args "`"$IDF_PATH/tools/check_python_dependencies.py`"" + if ($LASTEXITCODE -ne 0) { exit $LASTEXITCODE } # if error + + Write-Output " +Done! You can now compile ESP-IDF projects. +Go to the project directory and run: + idf.py build +" + +} diff --git a/tools/windows/tool_setup/idf_setup.iss.inc b/tools/windows/tool_setup/idf_setup.iss.inc index cfaaec429f..be2611d624 100644 --- a/tools/windows/tool_setup/idf_setup.iss.inc +++ b/tools/windows/tool_setup/idf_setup.iss.inc @@ -413,7 +413,38 @@ begin GetIDFPath(''), '', 0, SW_SHOWNORMAL); except - MsgBox('Failed to create the Start menu shortcut: ' + Destination, mbError, MB_OK); + MsgBox('Failed to create the shortcut: ' + Destination, mbError, MB_OK); + RaiseException('Failed to create the shortcut'); + end; +end; + +procedure CreateIDFPowershellShortcut(LnkString: String); +var + Destination: String; + Description: String; + Command: String; + GitPathWithForwardSlashes: String; + PythonPathWithForwardSlashes: String; +begin + ForceDirectories(ExpandConstant(LnkString)); + Destination := ExpandConstant(LnkString + '\{#IDFPsShortcutFile}'); + Description := '{#IDFPsShortcutDescription}'; + GitPathWithForwardSlashes := GitPath; + PythonPathWithForwardSlashes := PythonPath; + StringChangeEx(GitPathWithForwardSlashes, '\', '/', True); + StringChangeEx(PythonPathWithForwardSlashes, '\', '/', True); + Command := ExpandConstant('-ExecutionPolicy Bypass -NoExit -File ""{app}\idf_cmd_init.ps1"" ') + '"' + GitPathWithForwardSlashes + '" "' + PythonPathWithForwardSlashes + '"' + Log('CreateShellLink Destination=' + Destination + ' Description=' + Description + ' Command=' + Command) + try + CreateShellLink( + Destination, + Description, + 'powershell.exe', + Command, + GetIDFPath(''), + '', 0, SW_SHOWNORMAL); + except + MsgBox('Failed to create the shortcut: ' + Destination, mbError, MB_OK); RaiseException('Failed to create the shortcut'); end; end; diff --git a/tools/windows/tool_setup/idf_tool_setup.iss b/tools/windows/tool_setup/idf_tool_setup.iss index 269297ae3b..2a396baf0f 100644 --- a/tools/windows/tool_setup/idf_tool_setup.iss +++ b/tools/windows/tool_setup/idf_tool_setup.iss @@ -13,12 +13,17 @@ #define PythonInstallerName "idf-python-3.9.1-embed-win64.zip" #define PythonInstallerDownloadURL "https://dl.espressif.com/dl/idf-python/idf-python-3.9.1-embed-win64.zip" -#define GitVersion "2.21.0" -#define GitInstallerName "Git-2.21.0-64-bit.exe" -#define GitInstallerDownloadURL "https://github.com/git-for-windows/git/releases/download/v2.21.0.windows.1/Git-2.21.0-64-bit.exe" +#define GitVersion "2.28.0" +#define GitInstallerName "Git-2.28.0-64-bit.exe" +#define GitInstallerDownloadURL "https://github.com/git-for-windows/git/releases/download/v2.28.0.windows.1/Git-2.28.0-64-bit.exe" -#define IDFCmdExeShortcutDescription "Open ESP-IDF Command Prompt (cmd.exe)" -#define IDFCmdExeShortcutFile "ESP-IDF Command Prompt (cmd.exe).lnk" +#define IDFVersionsURL "https://dl.espressif.com/dl/esp-idf/idf_versions.txt" + +#define IDFCmdExeShortcutDescription "Open ESP-IDF Command Prompt (cmd.exe) Environment" +#define IDFCmdExeShortcutFile "ESP-IDF CMD.lnk" + +#define IDFPsShortcutDescription "Open ESP-IDF PowerShell Environment" +#define IDFPsShortcutFile "ESP-IDF PowerShell.lnk" [Setup] ; NOTE: The value of AppId uniquely identifies this application. @@ -62,6 +67,7 @@ Source: "..\..\idf_tools.py"; DestDir: "{app}"; DestName: "idf_tools_fallback.py ; Note: this tools.json matches the requirements of IDF v3.x versions. Source: "tools_fallback.json"; DestDir: "{app}"; DestName: "tools_fallback.json" Source: "idf_cmd_init.bat"; DestDir: "{app}" +Source: "idf_cmd_init.ps1"; DestDir: "{app}" Source: "dist\*"; DestDir: "{app}\dist" ; Helper Python files for sanity check of Python environment - used by system_check_page Source: "system_check\system_check_download.py"; Flags: dontcopy @@ -77,11 +83,15 @@ Type: filesandordirs; Name: "{app}\releases" Type: filesandordirs; Name: "{app}\tools" Type: filesandordirs; Name: "{app}\python_env" Type: files; Name: "{group}\{#IDFCmdExeShortcutFile}" +Type: files; Name: "{group}\{#IDFPsShortcutFile}" Type: files; Name: "{autodesktop}\{#IDFCmdExeShortcutFile}" +Type: files; Name: "{autodesktop}\{#IDFPsShortcutFile}" [Tasks] -Name: createlnk; Description: "Create Start Menu shortcut for the ESP-IDF Tools Command Prompt"; -Name: createdsk; Description: "Create Desktop shortcut for the ESP-IDF Tools Command Prompt"; +Name: CreateLnkStartCmd; Description: "Create Start Menu shortcut for the ESP-IDF Tools Command Prompt Environment"; +Name: CreateLnkStartPs; Description: "Create Start Menu shortcut for the ESP-IDF Tools Powershell Environment"; +Name: CreateLnkDeskCmd; Description: "Create Desktop shortcut for the ESP-IDF Tools Command Prompt Environment"; +Name: CreateLnkDeskPs; Description: "Create Desktop shortcut for the ESP-IDF Tools Powershell Environment"; ; WD registration checkbox is identified by 'Windows Defender' substring anywhere in its caption, not by the position index in WizardForm.TasksList.Items ; Please, keep this in mind when making changes to the item's description - WD checkbox is to be disabled on systems without the Windows Defender installed Name: wdexcl; Description: "Register the ESP-IDF Tools executables as Windows Defender exclusions (improves compilation speed, requires elevation)"; @@ -89,7 +99,9 @@ Name: idf_tools_use_mirror; Description: "Use Espressif download server instead [Run] Filename: "{app}\dist\{#GitInstallerName}"; Parameters: "/silent /tasks="""" /norestart"; Description: "Installing Git"; Check: GitInstallRequired -Filename: "{group}\{#IDFCmdExeShortcutFile}"; Flags: postinstall shellexec; Description: "Run ESP-IDF Command Prompt (cmd.exe)"; Check: InstallationSuccessful +Filename: "{group}\{#IDFPsShortcutFile}"; Flags: postinstall shellexec unchecked; Description: "Run ESP-IDF PowerShell Environment"; Check: IsPowerShellInstalled +Filename: "{group}\{#IDFCmdExeShortcutFile}"; Flags: postinstall shellexec unchecked; Description: "Run ESP-IDF Command Prompt Environment"; Check: IsCmdInstalled + [UninstallRun] Filename: "powershell.exe"; \ diff --git a/tools/windows/tool_setup/main.iss.inc b/tools/windows/tool_setup/main.iss.inc index 0649d38760..4c78299ce0 100644 --- a/tools/windows/tool_setup/main.iss.inc +++ b/tools/windows/tool_setup/main.iss.inc @@ -134,16 +134,26 @@ begin IDFToolsSetup(); - if WizardIsTaskSelected('createlnk') then + if WizardIsTaskSelected('CreateLnkStartCmd') then begin CreateIDFCommandPromptShortcut('{autostartmenu}\Programs\ESP-IDF'); end; - if WizardIsTaskSelected('createdsk') then + if WizardIsTaskSelected('CreateLnkStartPs') then + begin + CreateIDFPowershellShortcut('{autostartmenu}\Programs\ESP-IDF' ); + end; + + if WizardIsTaskSelected('CreateLnkDeskCmd') then begin CreateIDFCommandPromptShortcut('{autodesktop}'); end; + if WizardIsTaskSelected('CreateLnkDeskPs') then + begin + CreateIDFPowershellShortcut('{autodesktop}'); + end; + if WizardIsTaskSelected('wdexcl') then begin RegisterIDFToolsExecutablesInWD(); @@ -170,3 +180,14 @@ begin Result := SetupAborted; end; end; + + +function IsPowerShellInstalled(): Boolean; +begin + Result := ((not SetupAborted) and (WizardIsTaskSelected('CreateLnkDeskPs') or WizardIsTaskSelected('CreateLnkStartPs'))); +end; + +function IsCmdInstalled(): Boolean; +begin + Result := ((not SetupAborted) and (WizardIsTaskSelected('CreateLnkDeskCmd') or WizardIsTaskSelected('CreateLnkStartCmd'))); +end;