Skip to content
This repository has been archived by the owner on Jul 5, 2024. It is now read-only.

Commit

Permalink
Some utility code clean up
Browse files Browse the repository at this point in the history
  • Loading branch information
caesay committed Dec 26, 2023
1 parent 7a482a6 commit ad4fdb4
Show file tree
Hide file tree
Showing 14 changed files with 167 additions and 549 deletions.
42 changes: 38 additions & 4 deletions src/Squirrel.Packaging.OSX/HelperExe.cs
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
using System.Runtime.Versioning;
using System.ComponentModel;
using System.Runtime.InteropServices;
using System.Runtime.Versioning;
using System.Security;
using Microsoft.Extensions.Logging;
using Newtonsoft.Json;
Expand Down Expand Up @@ -98,7 +100,7 @@ public void SpctlAssessInstaller(string filePath)
// https://stackoverflow.com/questions/35619036/open-app-after-installation-from-pkg-file-in-mac
var postinstall = Path.Combine(tmpScripts, "postinstall");
File.WriteAllText(postinstall, $"#!/bin/sh\nsudo -u \"$USER\" open \"$2/{bundleName}/\"\nexit 0");
PlatformUtil.ChmodFileAsExecutable(postinstall);
ChmodFileAsExecutable(postinstall);

// generate non-relocatable component pkg. this will be included into a product archive
var pkgPlistPath = Path.Combine(tmp, "tmp.plist");
Expand Down Expand Up @@ -172,7 +174,7 @@ public void Notarize(string filePath, string keychainProfileName)
filePath
};

var ntresultjson = PlatformUtil.InvokeProcess("xcrun", args, null, CancellationToken.None);
var ntresultjson = InvokeProcess("xcrun", args, null);
Log.Info(ntresultjson.StdOutput);

// try to catch any notarization errors. if we have a submission id, retrieve notary logs.
Expand All @@ -187,7 +189,7 @@ public void Notarize(string filePath, string keychainProfileName)
"--keychain-profile", keychainProfileName,
};

var result = PlatformUtil.InvokeProcess("xcrun", logargs, null, CancellationToken.None);
var result = InvokeProcess("xcrun", logargs, null);
Log.Warn(result.StdOutput);
}

Expand Down Expand Up @@ -232,4 +234,36 @@ public void CreateDittoZip(string folder, string outputZip)
Log.Info($"Creating ditto bundle '{outputZip}'");
InvokeAndThrowIfNonZero("ditto", args, null);
}

private const string OSX_CSTD_LIB = "libSystem.dylib";
private const string NIX_CSTD_LIB = "libc";

[SupportedOSPlatform("osx")]
[DllImport(OSX_CSTD_LIB, EntryPoint = "chmod", SetLastError = true)]
private static extern int osx_chmod(string pathname, int mode);

[SupportedOSPlatform("linux")]
[DllImport(NIX_CSTD_LIB, EntryPoint = "chmod", SetLastError = true)]
private static extern int nix_chmod(string pathname, int mode);

protected static void ChmodFileAsExecutable(string filePath)
{
Func<string, int, int> chmod;

if (SquirrelRuntimeInfo.IsOSX) chmod = osx_chmod;
else if (SquirrelRuntimeInfo.IsLinux) chmod = nix_chmod;
else return; // no-op on windows, all .exe files can be executed.

var filePermissionOctal = Convert.ToInt32("777", 8);
const int EINTR = 4;
int chmodReturnCode;

do {
chmodReturnCode = chmod(filePath, filePermissionOctal);
} while (chmodReturnCode == -1 && Marshal.GetLastWin32Error() == EINTR);

if (chmodReturnCode == -1) {
throw new Win32Exception(Marshal.GetLastWin32Error(), $"Could not set file permission {filePermissionOctal} for {filePath}.");
}
}
}
43 changes: 39 additions & 4 deletions src/Squirrel.Packaging.Windows/HelperExe.cs
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
using System.Runtime.Versioning;
using System.ComponentModel;
using System.Runtime.InteropServices;
using System.Runtime.Versioning;
using System.Text;
using System.Text.RegularExpressions;
using Microsoft.Extensions.Logging;
Expand Down Expand Up @@ -68,7 +70,7 @@ public void SignPEFilesWithSignTool(string rootDir, string[] filePaths, string s
}

var totalToSign = pendingSign.Count;
var baseSignArgs = PlatformUtil.CommandLineToArgvW(signArguments);
var baseSignArgs = CommandLineToArgvW(signArguments);

do {
List<string> args = new List<string>();
Expand All @@ -78,7 +80,7 @@ public void SignPEFilesWithSignTool(string rootDir, string[] filePaths, string s
args.Add(pendingSign.Dequeue());
}

var result = PlatformUtil.InvokeProcess(SignToolPath, args, rootDir, CancellationToken.None);
var result = InvokeProcess(SignToolPath, args, rootDir);
if (result.ExitCode != 0) {
var cmdWithPasswordHidden = new Regex(@"\/p\s+?[^\s]+").Replace(result.Command, "/p ********");
Log.Debug($"Signing command failed: {cmdWithPasswordHidden}");
Expand All @@ -101,7 +103,7 @@ public void SignPEFileWithTemplate(string filePath, string signTemplate)

var command = signTemplate.Replace("\"{{file}}\"", "{{file}}").Replace("{{file}}", $"\"{filePath}\"");

var result = PlatformUtil.InvokeProcess(command, null, null, CancellationToken.None);
var result = InvokeProcess(command, null, null);
if (result.ExitCode != 0) {
var cmdWithPasswordHidden = new Regex(@"\/p\s+?[^\s]+").Replace(result.Command, "/p ********");
Log.Debug($"Signing command failed: {cmdWithPasswordHidden}");
Expand Down Expand Up @@ -144,4 +146,37 @@ public void SetPEVersionBlockFromPackageInfo(string exePath, NuGet.IPackage pack

Utility.Retry(() => InvokeAndThrowIfNonZero(RceditPath, args, null));
}

private const string WIN_KERNEL32 = "kernel32.dll";
private const string WIN_SHELL32 = "shell32.dll";

[SupportedOSPlatform("windows")]
[DllImport(WIN_KERNEL32, EntryPoint = "LocalFree", SetLastError = true)]
private static extern IntPtr _LocalFree(IntPtr hMem);

[SupportedOSPlatform("windows")]
[DllImport(WIN_SHELL32, EntryPoint = "CommandLineToArgvW", CharSet = CharSet.Unicode)]
private static extern IntPtr _CommandLineToArgvW([MarshalAs(UnmanagedType.LPWStr)] string cmdLine, out int numArgs);

[SupportedOSPlatform("windows")]
protected static string[] CommandLineToArgvW(string cmdLine)
{
IntPtr argv = IntPtr.Zero;
try {
argv = _CommandLineToArgvW(cmdLine, out var numArgs);
if (argv == IntPtr.Zero) {
throw new Win32Exception();
}
var result = new string[numArgs];

for (int i = 0; i < numArgs; i++) {
IntPtr currArg = Marshal.ReadIntPtr(argv, i * Marshal.SizeOf(typeof(IntPtr)));
result[i] = Marshal.PtrToStringUni(currArg);
}

return result;
} finally {
_LocalFree(argv);
}
}
}
48 changes: 46 additions & 2 deletions src/Squirrel.Packaging/HelperFile.cs
Original file line number Diff line number Diff line change
@@ -1,4 +1,8 @@
using System.Reflection;
using System.ComponentModel;
using System.Diagnostics;
using System.Reflection;
using System.Runtime.InteropServices;
using System.Runtime.Versioning;
using Microsoft.Extensions.Logging;

namespace Squirrel.Packaging;
Expand Down Expand Up @@ -88,8 +92,48 @@ protected static string FindHelperFile(string toFind, Func<string, bool> predica

protected static string InvokeAndThrowIfNonZero(string exePath, IEnumerable<string> args, string workingDir)
{
var result = PlatformUtil.InvokeProcess(exePath, args, workingDir, CancellationToken.None);
var result = InvokeProcess(exePath, args, workingDir);
ProcessFailedException.ThrowIfNonZero(result);
return result.StdOutput;
}

protected static (int ExitCode, string StdOutput) InvokeProcess(ProcessStartInfo psi, CancellationToken ct)
{
var pi = Process.Start(psi);
while (!ct.IsCancellationRequested) {
if (pi.WaitForExit(500)) break;
}

if (ct.IsCancellationRequested && !pi.HasExited) {
pi.Kill();
ct.ThrowIfCancellationRequested();
}

string output = pi.StandardOutput.ReadToEnd();
string error = pi.StandardError.ReadToEnd();
var all = (output ?? "") + Environment.NewLine + (error ?? "");

return (pi.ExitCode, all.Trim());
}

protected static (int ExitCode, string StdOutput, string Command) InvokeProcess(string fileName, IEnumerable<string> args, string workingDirectory, CancellationToken ct = default)
{
var psi = CreateProcessStartInfo(fileName, workingDirectory);
psi.AppendArgumentListSafe(args, out var argString);
var p = InvokeProcess(psi, ct);
return (p.ExitCode, p.StdOutput, $"{fileName} {argString}");
}

protected static ProcessStartInfo CreateProcessStartInfo(string fileName, string workingDirectory)
{
var psi = new ProcessStartInfo(fileName);
psi.UseShellExecute = false;
psi.WindowStyle = ProcessWindowStyle.Hidden;
psi.ErrorDialog = false;
psi.CreateNoWindow = true;
psi.RedirectStandardOutput = true;
psi.RedirectStandardError = true;
psi.WorkingDirectory = workingDirectory ?? Environment.CurrentDirectory;
return psi;
}
}
3 changes: 1 addition & 2 deletions src/Squirrel/Compression/BZip2Stream.cs
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
#pragma warning disable CS1591 // Missing XML comment for publicly visible type or member
using System;
using System;
using System.IO;
using System.IO.Compression;

Expand Down
3 changes: 1 addition & 2 deletions src/Squirrel/Compression/BinaryPatchUtility.cs
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
#pragma warning disable CS1591 // Missing XML comment for publicly visible type or member
using System;
using System;
using System.IO;
using System.IO.Compression;
using System.Threading;
Expand Down
2 changes: 2 additions & 0 deletions src/Squirrel/Internal/Disposable.cs
Original file line number Diff line number Diff line change
@@ -1,8 +1,10 @@
using System;
using System.Diagnostics.CodeAnalysis;
using System.Threading;

namespace Squirrel
{
[ExcludeFromCodeCoverage]
internal static class Disposable
{
public static IDisposable Create(Action action)
Expand Down
3 changes: 1 addition & 2 deletions src/Squirrel/Internal/LoggerExtensions.cs
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
#pragma warning disable CS1591 // Missing XML comment for publicly visible type or member
using System;
using System;
using System.Diagnostics.CodeAnalysis;
using Microsoft.Extensions.Logging;

Expand Down
Loading

0 comments on commit ad4fdb4

Please sign in to comment.