internal void StartPackageManager() { // ok, we're looking like we're ready to need the package manager. // make sure its running. PackageManager.Instance.ConnectAndWait("autopackage", null, 15000); PackageManager = PackageManager.Instance; PackageManager.AddFeed(Environment.CurrentDirectory,true); if (AutopackageMain._verbose) { PackageManager.SetLogging(true, true, true); } }
/// <summary> /// The (non-static) startup method /// </summary> /// <param name = "args"> /// The command line arguments. /// </param> /// <returns> /// Process return code. /// </returns> protected override int Main(IEnumerable<string> args) { try { _package.CertificateFile = _certificateSettings["#CurrentCertificate"].EncryptedStringValue; PackageManager.Instance.Connect("autopackage"); if (!PackageManager.Instance.IsReady.WaitOne(5000)) { //Verbose("# not connected..."); throw new ConsoleException("# Unable to connect to CoApp Service."); } _pkgMgr = PackageManager.Instance; PropertySheet propSheet; _pkgMgr.AddFeed(Environment.CurrentDirectory); var exceptions = new List<Exception>(); #region command line parsing var configLoaded = false; // default: var options = args.Switches(); var parameters = args.Parameters(); foreach (var arg in options.Keys) { var argumentParameters = options[arg]; switch (arg) { /* options */ /* global switches */ case "load-config": // all ready done, but don't get too picky. break; case "load": propSheet = PropertySheet.Load(argumentParameters.First()); PropSheetParser parser = new PropSheetParser(_package); //parser.Parse(propSheet); configLoaded = true; break; case "nologo": this.Assembly().SetLogo(string.Empty); break; case "show-tools": _showTools = Boolean.Parse(argumentParameters.First()); break; case "password": _package.CertificatePassword = argumentParameters.First(); break; case "autosign": _autosign = true; break; case "remember": _remember = true; break; case "accept-old-bs": _acceptOldBs = true; break; case "help": return Help(); default: throw new ConsoleException(Resources.UnknownParameter, arg); } } Logo(); if (!configLoaded) throw new ConsoleException(Resources.NoConfigFileLoaded); #endregion // GS01: I'm putting this in here so that feed resoltion happens before we actually get around to doing something. // Look into the necessity later. // Tasklet.WaitforCurrentChildTasks(); #region Tool Scanning Console.Write(Resources.ToolLookup); _candle = new ProcessUtility(ProgramFinder.ProgramFilesAndDotNet.ScanForFile("candle.exe")); _light = new ProcessUtility(ProgramFinder.ProgramFilesAndDotNet.ScanForFile("light.exe")); _mt = new ProcessUtility(ProgramFinder.ProgramFilesAndDotNet.ScanForFile("mt.exe")); _makecat = new ProcessUtility(ProgramFinder.ProgramFilesAndDotNet.ScanForFile("makecat.exe")); _al = new ProcessUtility(ProgramFinder.ProgramFilesAndDotNet.ScanForFile("al.exe")); _signTool = new ProcessUtility(ProgramFinder.ProgramFilesAndDotNet.ScanForFile("signTool.exe")); _sn = new ProcessUtility(ProgramFinder.ProgramFilesAndDotNet.ScanForFile("sn.exe")); if (_candle.Executable == null) exceptions.Add(CreateEndUserException(144)); if (_light.Executable == null) exceptions.Add(CreateEndUserException(145)); if (_mt.Executable == null) exceptions.Add(CreateEndUserException(146)); if (_makecat.Executable == null) exceptions.Add(CreateEndUserException(147)); if (_al.Executable == null) exceptions.Add(CreateEndUserException(148)); if (_signTool.Executable == null) exceptions.Add(CreateEndUserException(149)); if (_sn.Executable == null) exceptions.Add(CreateEndUserException(150)); if (exceptions.Count > 0) { throw new AggregateException(exceptions); } Console.WriteLine(Resources.Finished); if (_showTools) { Console.WriteLine("Tools:"); Console.WriteLine(_candle.Executable); Console.WriteLine(_light.Executable); Console.WriteLine(_mt.Executable); Console.WriteLine(_makecat.Executable); Console.WriteLine(_al.Executable); Console.WriteLine(_sn.Executable); Console.WriteLine(_signTool.Executable); } ReadPassword(); #endregion Console.WriteLine(Resources.ScanningInstalledPackages); //TODO What will happen when we have feeds in other places???? IEnumerable<Package> allPackages = null; /* var tsk = _pkgMgr.GetPackagesInScanLocations(new PackageManagerMessages { PackageScanning = (progress) => Resources.Scanning.PrintProgressBar(progress) }).ContinueWith((antecedent) => { allPackages = antecedent.Result; " ".PrintProgressBar(100); Console.WriteLine("\r"); },TaskContinuationOptions.AttachedToParent); tsk.Wait(); */ //find all the files that need to be found recursively //verify that the lefthand side of includes are valid subpaths foreach (var i in _package.AllIncludes.Keys) { foreach (var include in _package.AllIncludes[i]) { if (!include.L.IsSimpleSubPath()) { exceptions.Add(CreateEndUserPropertyException(i.IncludeToProp[include.L], 160, include.L)); } } } if (_package.Apps != null) { if (_package.Apps.GlobalBinEntry != null) { if (!_package.Apps.GlobalBinEntry.IsBoolean()) { exceptions.Add(CreateEndUserPropertyException(_package.Apps.GlobalBinEntryProp, 152)); } else { _package.Apps.GlobalBin = Boolean.Parse(_package.Apps.GlobalBinEntry); } } _package.Apps.EvaluateIncludes(); //set up the input files foreach (var e in _package.Apps.PrimaryExes) { var input = (from a in _package.Apps.FinalInclude where a.R.Path.IsWildcardMatch(e.ExeFile) select a).FirstOrDefault(); if (input == null) { if (!File.Exists(e.ExeFile)) exceptions.Add(CreateEndUserException(153, e.ExeFile)); else { //Exefile wasn't found in the Includes but it really does exist _package.Apps.FinalInclude = _package.Apps.FinalInclude.Concat(new OutputTup { L = new FileInfo(e.ExeFile.Original).Name, R = e.ExeFile }.SingleItemAsEnumerable()); } } else { e.ExeFile = input.R; } if (e.GlobalBinEntry != null) { if (!e.GlobalBinEntry.IsBoolean()) { exceptions.Add(CreateEndUserPropertyException(e.GlobalBinEntryProp, 152)); } else { e.GlobalBin = Boolean.Parse(e.GlobalBinEntry); } } } } if (_package.SharedLibs != null) { var shared = _package.SharedLibs; var sharedEntryValid = false; if (shared.GlobalEntry != null) { if (!shared.GlobalEntry.IsBoolean()) { exceptions.Add(CreateEndUserPropertyException(shared.GlobalEntryProp, 170)); } else { shared.Global = Boolean.Parse(shared.GlobalEntry); sharedEntryValid = true; } } foreach (var a in _package.SharedLibs.Assemblies) { a.EvaluateIncludes(true); if (a.GlobalEntry != null) { if (!a.GlobalEntry.IsBoolean()) { exceptions.Add(CreateEndUserPropertyException(a.GlobalEntryProp, 170)); } else { a.Global = Boolean.Parse(a.GlobalEntry); } } else if (sharedEntryValid) { a.Global = shared.Global; } } } if (_package.DeveloperLibs != null) { BasicIncludeAndExclude[] items = { _package.DeveloperLibs.Headers, _package.DeveloperLibs.ImportLibs, _package.DeveloperLibs.StaticLibs }; foreach (var sec in items) { if (sec.GlobalLinkEntry != null) { if (!sec.GlobalLinkEntry.IsBoolean()) { exceptions.Add(CreateEndUserPropertyException(sec.GlobalLinkEntryProp, 169)); } else { sec.GlobalLink = Boolean.Parse(sec.GlobalLinkEntry); } } sec.EvaluateIncludes(); } //add the proper prefix to all the files _package.DeveloperLibs.Headers.AddPrefix(HEADERS_DIR_NAME); _package.DeveloperLibs.ImportLibs.AddPrefix(IMPORTLIB_DIR_NAME); _package.DeveloperLibs.StaticLibs.AddPrefix(STATICLIB_DIR_NAME); } if (_package.SourceCodes != null) { var sc = _package.SourceCodes; sc.EvaluateIncludes(); sc.AddPrefix(SRC_DIR_NAME); } //copy all the stuff that needs to go to Temp TO Temp _package.Prepare(); foreach (var dep in _package.DependencyNames) { /* var temp = new EditableTup<string, string> {L = dep.L, R = _package.ResolveVariables(dep.R)}; //TODO this doesn't work if a packages is a superceding version of the one given var depPackage = (from p in allPackages where p.CosmeticName.IsWildcardMatch(temp.R) orderby p.Version descending select p).FirstOrDefault(); if (depPackage == null) { if (_package.DependencyNamesProp.ContainsKey(temp.R)) { exceptions.Add(CreateEndUserPropertyException(_package.DependencyNamesProp[dep.R], 133, dep.R)); } else { exceptions.Add(CreateEndUserException(133, dep.R)); } } else { _package.DependencyInfo.Add(depPackage); }*/ } //TODO make sure the numbers are not larger than the max a part of a version string var policyRegex = new Regex(@"^policy\.\d{1,5}\.\d{1,5}\.\S+$"); /* var dependentAssemblies = from p in _package.DependencyInfo from a in p.Assemblies where !a.Type.Contains("policy") && !policyRegex.IsMatch(a.Name) select a; */ //let's check for valid roles! if (_package.Roles.IsNullOrEmpty()) exceptions.Add(CreateEndUserException(131)); //make sure the major minors given are valid if (_package.SharedLibs != null) { foreach (var i in _package.SharedLibs.MajorMinorsToReplace) { if (!i.IsValidMajorMinorVersion()) { if (_package.SharedLibs.MajorMinorsToReplaceProp.ContainsKey(i)) { exceptions.Add(CreateEndUserPropertyException(_package.SharedLibs.MajorMinorsToReplaceProp[i], 132, i)); } else { exceptions.Add(CreateEndUserException(132, i)); } } } } if (_package.Apps != null) { foreach (var e in _package.Apps.PrimaryExes) { if (e.StartMenu != null) { if (!e.StartMenu.IsSimpleSubPath()) { exceptions.Add(CreateEndUserPropertyException(e.StartMenuProp, 168, e.StartMenu)); continue; } if (!e.StartMenu.EndsWith(".lnk")) { e.StartMenu += ".lnk"; } } } } if (exceptions.Count > 0) { throw new AggregateException(exceptions); } #region Handle Shared Libraries //first create the string of all the dependencies elements var sharedlib = _package.SharedLibs; if (sharedlib != null) { //set all the assembly names properly foreach (var a in sharedlib.Assemblies) { if (a.Name == null) { var fi = new FileInfo(a.PrimaryFile); a.Name = fi.NameWithoutExt().Replace(" ", "_"); } } Console.Write(Resources.SharedLibCreation); if (_package.PackageArch != "any") { var dependencyStr = new StringBuilder(); /* foreach (var dep in dependentAssemblies) { dependencyStr.Append(DependencyEntry.Replace("[$LIBTYPE]", dep.Type).Replace("[$LIBNAME]", dep.Name). Replace("[$LIBVERSION]", dep.Version).Replace("[$ARCH]", dep.Arch). Replace("[$PUBLICKEYTOKEN]", dep.PublicKeyToken)); } */ foreach (var a in sharedlib.Assemblies) { /* var manifestFilesString = new StringBuilder(); var filesString = new StringBuilder(); filesString.Append(FileEntry.Replace("[$FILE]", Path.GetFileName(a.PrimaryFile))); foreach (var f in a.FinalInclude) { filesString.Append(FileEntry.Replace("[$FILE]", f.L)); } manifestFilesString.Append(SharedLibraryManifest.Replace("[$LIBNAME]", a.Name). Replace("[$LIBVERSION]", _package.PackageVersion). Replace("[$DEPENDENCY]", dependencyStr.ToString()).Replace("[$PUBLICKEYTOKEN]", _package.PubToken). Replace("[$ARCH]", _package.PackageArch).Replace("[$FILES]", filesString.ToString())); a.Manifest = Path.Combine(new FileInfo(a.PrimaryFile).DirectoryName, a.PrimaryFile + ".manifest"); //TODO do file checking File.WriteAllText(a.Manifest, manifestFilesString.ToString()); */ // sign all the non-primary BinFiles var binFiles = from f in a.FinalInclude.BinaryFiles() select f.R; exceptions.AddRange(VerifySigning(binFiles, false)); //manifest created. Let's embed it. if (!EmbedManifest(a.PrimaryFile)) { exceptions.Add(CreateEndUserException(137, a.PrimaryFile + ".manifest", a.PrimaryFile)); continue; } //sign the primary file if (!SignFile(a.PrimaryFile)) { exceptions.Add(CreateEndUserException(136, a.PrimaryFile)); continue; } a.CatFile = a.PrimaryFile + ".cat"; if (!CreateAndSignCat(a.Manifest)) { exceptions.Add(CreateEndUserException(138, a.Manifest + ".cdf")); continue; } //we're going to create the policy assemblies foreach (var p in _package.SharedLibs.MajorMinorsToReplace) { var pa = new PolicyAssemblyDescription(p, a.Name); _package.SharedLibs.PolicyAssemblies.Add(pa); var paManifestString = PublisherConfiguration.Replace("[$ASSMNAME]", a.Name). Replace("[$LIBMAJORMINOR]", p).Replace("[$PUBLICKEYTOKEN]", _package.PubToken). Replace("[$LIBVERSION]", _package.PackageVersion).Replace("[$ARCH]", _package.PackageArch). Replace("[$OLDVERSION]", _package.BindingPolicy); pa.Manifest = Path.Combine(new FileInfo(a.PrimaryFile).DirectoryName, pa.Name + ".manifest"); File.WriteAllText(pa.Manifest, paManifestString); pa.CatFile = pa.Manifest.Replace(".manifest", "") + ".cat"; if (!CreateAndSignCat(pa.Manifest)) { exceptions.Add(CreateEndUserException(138, pa.Manifest + ".cdf")); continue; } } } } else { // it's .NET foreach (var a in sharedlib.Assemblies) { if (!_codeSigningCert.FinishStrongNaming(a.PrimaryFile)) { exceptions.Add(CreateEndUserException(139, a.PrimaryFile)); continue; } if (!SignFile(a.PrimaryFile)) { exceptions.Add(CreateEndUserException(136, a.PrimaryFile)); continue; } foreach (var p in _package.SharedLibs.MajorMinorsToReplace) { var pa = new PolicyAssemblyDescription(p, a.Name); _package.SharedLibs.PolicyAssemblies.Add(pa); pa.PrimaryFile = Path.Combine(new FileInfo(a.PrimaryFile).DirectoryName, pa.Name + ".dll"); var paManifestString = MSILPublisherConfiguration.Replace("[$ASSMNAME]", a.Name). Replace("[$PUBLICKEYTOKEN]", _package.PubToken). Replace("[$LIBVERSION]", _package.PackageVersion). Replace("[$OLDVERSION]", _package.BindingMin + "-" + _package.BindingMax); pa.Manifest = pa.PrimaryFile + ".config"; // cleanupFiles.Add(pa.Manifest); File.WriteAllText(pa.Manifest, paManifestString); if (!ExtractPublicKey()) { exceptions.Add(CreateEndUserPropertyException(_package.SharedLibs.MajorMinorsToReplaceProp[p], 140, _package.CertificateFile)); continue; } if (_al.Exec("/link:{0} /out:{1} /delaysign+ /keyfile:{2} /v:{3}", pa.Manifest, pa.PrimaryFile, _publicKeyFile, _package.PackageVersion) != 0) { exceptions.Add(CreateEndUserPropertyException(_package.SharedLibs.MajorMinorsToReplaceProp[p], 141, pa.PrimaryFile)); continue; } if (!_codeSigningCert.FinishStrongNaming(pa.PrimaryFile)) { exceptions.Add(CreateEndUserPropertyException(_package.SharedLibs.MajorMinorsToReplaceProp[p], 139, pa.PrimaryFile)); continue; } if (!SignFile(pa.PrimaryFile)) { exceptions.Add(CreateEndUserPropertyException(_package.SharedLibs.MajorMinorsToReplaceProp[p], 136, pa.PrimaryFile)); continue; } } } } if (exceptions.Count > 0) { throw new AggregateException(exceptions); } Console.WriteLine(Resources.Finished); } #endregion #region Handle Apps var apps = _package.Apps; if (apps != null) { Console.Write(Resources.AppCreation); if (_package.PackageArch != "any") { //it's native var dependencyStr = new StringBuilder(); /* foreach (var dep in dependentAssemblies) { dependencyStr.Append(DependencyEntry.Replace("[$LIBTYPE]", dep.Type).Replace("[$LIBNAME]", dep.Name). Replace("[$LIBVERSION]", dep.Version).Replace("[$ARCH]", dep.Arch). Replace("[$PUBLICKEYTOKEN]", dep.PublicKeyToken)); } //we needs to add in the other assemblies in this package if (sharedlib != null) { foreach (var dep in sharedlib.Assemblies) { dependencyStr.Append(DependencyEntry.Replace("[$LIBTYPE]", "win32"). Replace("[$LIBNAME]", dep.Name).Replace("[$LIBVERSION]", _package.PackageVersion). Replace("[$ARCH]", _package.PackageArch).Replace("[$PUBLICKEYTOKEN]", _package.PubToken)); } }*/ foreach (var e in apps.PrimaryExes) { /* if (dependencyStr.Length > 0) { var configFilename = e.InputFile + ".config"; var execManifest = new StringBuilder(); execManifest.Append(ExecutableManifest.Replace("[$DEPENDENCY]", dependencyStr.ToString())); File.WriteAllText(configFilename, execManifest.ToString()); if (!EmbedManifest(e.InputFile, configFilename)) { exceptions.Add(CreateEndUserException(137, configFilename, e.InputFile)); continue; } }*/ if (!SignFile(e.InputFile)) { exceptions.Add(CreateEndUserException(136, e.InputFile)); continue; } } } else { //it's .net foreach (var e in apps.PrimaryExes) { if (!_codeSigningCert.FinishStrongNaming(e.InputFile)) { exceptions.Add(CreateEndUserException(139, e.InputFile)); continue; } if (!SignFile(e.InputFile)) { exceptions.Add(CreateEndUserException(136, e.InputFile)); continue; } } } if (exceptions.Count > 0) { throw new AggregateException(exceptions); } Console.WriteLine(Resources.Finished); } //check if every binary is actually signed at all //yes this is really messy var binFilesToCheck = Enumerable.Empty<TempedFile>(); if (apps != null) binFilesToCheck = binFilesToCheck.Concat(from i in apps.BinaryFilesMinusPrimaries select i.R); if (_package.SourceCodes != null) binFilesToCheck = binFilesToCheck.Concat(from i in _package.SourceCodes.FinalInclude.BinaryFiles() select i.R); if (_package.DeveloperLibs != null) binFilesToCheck = binFilesToCheck.Concat(from i in _package.DeveloperLibs.Headers.FinalInclude. Concat(_package.DeveloperLibs.ImportLibs.FinalInclude). Concat(_package.DeveloperLibs.StaticLibs.FinalInclude). BinaryFiles() select i.R); exceptions.AddRange(VerifySigning(binFilesToCheck)); exceptions.AddRange(DownloadBootstrapManifest()); if (exceptions.Count > 0) { throw new AggregateException(exceptions); } #endregion #region Write Msi OutToFile Console.Write(Resources.CreatingMSI); var tempPrefix = Path.GetTempFileName(); File.WriteAllText(tempPrefix + ".wxs", _package.ConvertToWix()); //we suppress the lack of UpgradeCode warning since we don't use them if (_candle.Exec("-nologo -sw1075 -out {0}.wixobj {0}.wxs", tempPrefix) != 0) exceptions.Add(CreateEndUserException(142, _candle.StandardOut)); if (exceptions.Count > 0) { throw new AggregateException(exceptions); } //we suppress the lack of UpgradeCode warning since we don't use them if (_light.Exec("-nologo -sw1076 -out {1} {0}.wixobj", tempPrefix, _package.DefaultOutputFile) != 0) exceptions.Add(CreateEndUserException(143, _light.StandardOut)); if (exceptions.Count > 0) { throw new AggregateException(exceptions); } if (!SignFile(_package.DefaultOutputFile)) { exceptions.Add(CreateEndUserException(136, _package.DefaultOutputFile)); } if (exceptions.Count > 0) { throw new AggregateException(exceptions); } if (_remember) { //Verbose("Storing certificate details in the registry."); _certificateSettings["#CurrentCertificate"].EncryptedStringValue = _package.CertificateFile; _certificateSettings[Path.GetFileName(_package.CertificateFile), "Password"].EncryptedStringValue = _package.CertificatePassword; } Console.WriteLine(Resources.Finished); #endregion } catch (AggregateException failures) { CancellationTokenSource.Cancel(); Fail("{0}\r\n\r\n {1}", failures.InnerExceptions, Resources.ForCommandLineHelp); } catch (Exception failure) { CancellationTokenSource.Cancel(); Fail("{0}\r\n\r\n {1}", "{0} - stacktrace: {1}".format(failure.Message, failure.StackTrace) , Resources.ForCommandLineHelp); } finally { foreach (var f in _cleanupFiles) { File.Delete(f); } } return 0; }