// Called on the main thread in a macro context
            public void Refresh()
            {
                if (_regInfoNotAvailable)
                {
                    return;
                }

                object regInfoResponse = ExcelIntegration.GetRegistrationInfo(_xllPath, _version);

                if (regInfoResponse.Equals(ExcelError.ExcelErrorNA))
                {
                    _regInfoNotAvailable = true;
                    Logger.Provider.Info($"XllRegistrationInfo not available for {_xllPath}");
                    return;
                }

                if (regInfoResponse == null || regInfoResponse.Equals(ExcelError.ExcelErrorNum))
                {
                    // no update - versions match
                    return;
                }

                _regInfo = regInfoResponse as object[, ];
                if (_regInfo != null)
                {
                    Debug.Assert((string)_regInfo[0, 0] == _xllPath);
                    _version = (double)_regInfo[0, 1];
                }
            }
    public static void RegistrationInfo()
    {
        try
        {
            Excel.Application Application = ExcelDnaUtil.Application as Excel.Application;
            List <string>     addinPaths  = new List <string>();

            if (ExcelDnaUtil.ExcelVersion >= 14.0)
            {
                foreach (dynamic addIn in Application.AddIns2)
                {
                    if (addIn.IsOpen)
                    {
                        addinPaths.Add(addIn.FullName);
                    }
                }
            }
            else
            {
                HashSet <string> allPaths  = new HashSet <string>();
                dynamic          funcInfos = Application.RegisteredFunctions;
                if ((funcInfos != null))
                {
                    for (int i = funcInfos.GetLowerBound(0); i <= funcInfos.GetUpperBound(0); i++)
                    {
                        allPaths.Add(funcInfos[i, 1]);
                    }
                }
                addinPaths.AddRange(allPaths);
            }

            dynamic         wb      = Application.Workbooks.Add();
            Excel.Worksheet shIndex = wb.Sheets(1);
            shIndex.Name        = "Add-Ins";
            shIndex.Cells[1, 1] = "Add-In Path";
            shIndex.Cells[1, 2] = "Registration Info?";

            int row = 2;
            foreach (string path in addinPaths)
            {
                shIndex.Cells[row, 1] = path;

                // Try to read RegistrationInfo
                dynamic result = ExcelIntegration.GetRegistrationInfo(path, 0);
                if (result.Equals(ExcelError.ExcelErrorNA))
                {
                    shIndex.Cells[row, 2] = false;
                }
                else
                {
                    shIndex.Cells[row, 2] = true;

                    // Dump the result to a new sheet
                    Excel.Worksheet shInfo = wb.Sheets.Add(After: wb.Sheets(wb.Sheets.Count));
                    shInfo.Name = System.IO.Path.GetFileName(path);

                    // C API via ExcelReference would work well here
                    dynamic refInfo = new ExcelReference(0, result.GetUpperBound(0), 0, 254, shInfo.Name);
                    refInfo.SetValue(result);
                }
                row = row + 1;
            }
            shIndex.Activate();
        }
        catch (Exception ex)
        {
            Debug.Print(ex.ToString());
        }
    }
 public override object GetRegistrationInfo(string xllPath, double registrationUpdateVersion)
 {
     return(ExcelIntegration.GetRegistrationInfo(xllPath, registrationUpdateVersion));
 }