2016-04-22 2 views
2

Я написал следующий код:Как проверить, является ли файл сборки .NET в C#

public DataTable GetDotNetAssemblies(string baseDirectory) 
{ 
    DataTable MethodResult = null; 
    try 
    { 
     if (Directory.Exists(baseDirectory)) 
     { 
      List<string> FilePaths = NetworkConnection.GetAllFilesUnderDirectory(baseDirectory); 

      DataTable dt = new DataTable(); 
      dt.Columns.Add("Directory"); 
      dt.Columns.Add("Filename"); 
      dt.Columns.Add("Date modified"); 
      dt.Columns.Add("Bytes"); 
      dt.Columns.Add("User modified"); 

      foreach (string FilePath in FilePaths) 
      { 
       DataRow dr = dt.NewRow(); 

       FileInfo f = new FileInfo(FilePath); 

       List<string> AllowedExtensions = new List<string>(); 
       AllowedExtensions.Add(".exe"); 
       AllowedExtensions.Add(".dll"); 

       if (AllowedExtensions.Contains(f.Extension.ToLower())) 
       { 
        dr["Directory"] = f.Directory; 
        dr["Filename"] = f.Name; 
        dr["Date modified"] = f.LastWriteTime; 
        dr["Bytes"] = f.Length.ToString(); 

        string UserModified = ""; 

        try 
        { 
         UserModified = f.GetAccessControl().GetOwner(typeof(System.Security.Principal.NTAccount)).ToString(); 

        } 
        catch 
        { 
         UserModified = "Unknown"; 

        } 

        dr["User modified"] = UserModified; 

        dt.Rows.Add(dr); 

       } 

      } 

      dt.AcceptChanges(); 

      MethodResult = dt; 

     } 
     else 
     { 
      MessageBox.Show("Unable to connect to directory:\n" + baseDirectory); 

     } 

    } 
    catch (Exception ex) 
    { 
     ex.HandleException(); 
    } 
    return MethodResult; 
} 

Я уже фильтрацию по расширению файла, который вы можете увидеть на линии:

if (AllowedExtensions.Contains(f.Extension.ToLower())) 

Что мне нужно, так это фильтровать файлы сборки, проверяя, являются ли они сборками .Net или нет.

Есть ли тест, который я могу выполнить в файле?

Кроме того, если можно узнать, какая версия .Net CLR используется в сборке, это было бы лучше.

ответ

-1

Модифицированный код

Modified для фильтрации .Net сборок:

public DataTable GetDotNetAssemblies(string baseDirectory) 
    { 
     DataTable MethodResult = null; 
     try 
     { 
      if (Directory.Exists(baseDirectory)) 
      { 
       List<string> FilePaths = NetworkConnection.GetAllFilesUnderDirectory(baseDirectory); 

       DataTable dt = new DataTable(); 
       dt.Columns.Add("Directory"); 
       dt.Columns.Add("Filename"); 
       dt.Columns.Add("Date modified"); 
       dt.Columns.Add("Bytes"); 
       dt.Columns.Add("User modified"); 
       dt.Columns.Add(".Net CLR version"); 

       foreach (string FilePath in FilePaths) 
       { 
        DataRow dr = dt.NewRow(); 

        FileInfo f = new FileInfo(FilePath); 

        List<string> AllowedExtensions = new List<string>(); 
        AllowedExtensions.Add(".exe"); 
        AllowedExtensions.Add(".dll"); 

        bool IsDotNetAssembly = false; 

        try 
        { 
         AssemblyName a = AssemblyName.GetAssemblyName(FilePath); 

         IsDotNetAssembly = true; 

        } catch {} 

        if (AllowedExtensions.Contains(f.Extension.ToLower()) && IsDotNetAssembly) 
        { 
         dr["Directory"] = f.Directory; 
         dr["Filename"] = f.Name; 
         dr["Date modified"] = f.LastWriteTime; 
         dr["Bytes"] = f.Length.ToString(); 

         try 
         { 
          Assembly a = Assembly.GetAssembly(AssemblyName.GetAssemblyName(FilePath).GetType()); 

          dr[".Net CLR version"] = a.ImageRuntimeVersion.ToString(); 

         } 
         catch //(Exception ex2) 
         { 
          //ex2.HandleException(); 
         } 

         string UserModified = ""; 

         try 
         { 
          UserModified = f.GetAccessControl().GetOwner(typeof(System.Security.Principal.NTAccount)).ToString(); 

         } 
         catch 
         { 
          UserModified = "Unknown"; 

         } 

         dr["User modified"] = UserModified; 

         dt.Rows.Add(dr); 

        } 

       } 

       dt.AcceptChanges(); 

       MethodResult = dt; 

      } 
      else 
      { 
       MessageBox.Show("Unable to connect to directory:\n" + baseDirectory); 

      } 

     } 
     catch //(Exception ex) 
     { 
      //ex.HandleException(); 
     } 
     return MethodResult; 
    } 

Тест 1

Слегка модифицированная версия C#, например найден here.

Исключение будет выбрано, если файл не является сборкой .Net.

bool IsDotNetAssembly = false; 

try 
{ 
    AssemblyName a = AssemblyName.GetAssemblyName(FilePath); 

    IsDotNetAssembly = true; 

} catch {} 

Тест 2

Сообщает вашу версию CLR, которая является версией .NET компилятор:

Assembly a = Assembly.GetAssembly(AssemblyName.GetAssemblyName(FilePath).GetType()); 

dr[".Net CLR version"] = a.ImageRuntimeVersion.ToString(); 
3

Вы можете попробовать использовать метод GetAssemblyName(), чтобы попытаться решить, если это была фактическая сборка аналогична the technique mentioned in this MSDN documentation:

public string bool IsValidAssembly(string path) 
{ 
    try 
    { 
      // Attempt to resolve the assembly 
      var assembly = GetAssemblyName(path); 
      // Nothing blew up, so it's an assembly 
      return true; 
    } 
    catch(Exception ex) 
    { 
      // Something went wrong, it is not an assembly (specifically a 
      // BadImageFormatException will be thrown if it could be found 
      // but it was NOT a valid assembly 
      return false; 
    } 
} 

Таким образом, вы могли бы рассмотреть возможность использования его в вашем коде:

// Check that it is a valid extension and a valid assembly 
if (AllowedExtensions.Contains(f.Extension.ToLower()) && IsValidAssembly(FilePath)) 
{ 
    // At this point it should be valid, so continue 
} 
1

Я считаю, что вам может понадобиться использовать AssemblyName.GetAssemblyName(path) - он не загружает сборку, но открывает/закрывает файл, чтобы прочитать манифест сборки (и выбрасывает System.BadImageFormatException, если не все)

https://msdn.microsoft.com/en-us/library/system.reflection.assemblyname.getassemblyname.aspx

Смежные вопросы