노현종

C언어 Patch 함수명 추출

......@@ -69,13 +69,13 @@ namespace VulnCrawler
// var fields = VulnWorker.GetCriticalVariant(@"return _is_safe_url(url, host) and _is_safe_url(url.replace('\\', '/'), host)");
var c = new VulnC();
var fields = c.ExtractCriticalVariant(@"!DoReadFile (infile, &ds64_chunk, sizeof (DS64Chunk), &bcount) ||/* aaaa */");
var fields = c.ExtractCriticalVariant(@"if (s->session->peer != s->session->sess_cert->peer_key->x509)");
foreach (var item in fields)
{
Console.WriteLine(item);
}
// return;
var directorys = Directory.GetDirectories(@"c:\VulnPy");
var directorys = Directory.GetDirectories(@"c:\VulnC");
if (directorys.Length == 0) {
Console.WriteLine("Repository 목록 찾기 실패");
return;
......@@ -83,7 +83,7 @@ namespace VulnCrawler
// Repository 목록 만큼 반복함.
foreach (var directory in directorys) {
// 템플릿 패턴화 T : VulnAbstractCrawler
VulnWorker.Run<VulnPython>(directory);
VulnWorker.Run<VulnC>(directory);
}
}
......
......@@ -73,7 +73,9 @@ namespace VulnCrawler
#endregion
public void Init(string path) {
Console.WriteLine("로딩중");
Repository = new Repository(path);
Console.WriteLine("로딩 완료");
Commits = SearchCommits();
}
/// <summary>
......@@ -88,7 +90,7 @@ namespace VulnCrawler
/// <summary>
/// 커밋에서 검색할 정규식 문자열
/// </summary>
public string SearchCommitPattern => @"CVE-20\d\d-\d{4}";
public string SearchCommitPattern => @"CVE[ -]\d{4}[ -]\d{4}";
/// <summary>
/// 패치 코드에서 함수 찾을 정규식 패턴 문자열
/// </summary>
......@@ -142,6 +144,8 @@ namespace VulnCrawler
/// <returns>커밋 목록</returns>
public virtual IEnumerable<Commit> SearchCommits() {
// where => 조건에 맞는 것을 찾음(CVE-20\d\d-\d{4}로 시작하는 커밋만 골라냄)
Console.WriteLine("출력중");
Console.WriteLine(Repository.Commits.Count());
var commits = Repository.Commits
.Where(c => Regex.Match(c.Message, SearchCommitPattern, RegexOptions.IgnoreCase).Success)
.ToList();
......@@ -183,7 +187,7 @@ namespace VulnCrawler
// 메서드 정규식 패턴
string methodPattern = @"([a-zA-Z0-9_\.]+)\s*\(";
// 변수 정규식 패턴
string fieldPattern = @"^*?[a-zA-Z0-9_\.\[\]]+";
string fieldPattern = @"^*?[a-zA-Z0-9_\.\[\]\-\>]+";
string invalidPattern = @"^[\d\.]+";
......
......@@ -10,7 +10,7 @@ namespace VulnCrawler
{
public class VulnC : VulnAbstractCrawler
{
protected override string RegexFuncPattern => $@"@@ \-(?<{OldStart}>\d+),(?<{OldLines}>\d+) \+(?<{NewStart}>\d+),(?<{NewLines}>\d+) @@ (?<{MethodName}>(static)? [\w]+ [\w]+)\([\w \*\,\t\n]*\)";
protected override string RegexFuncPattern => $@"@@ \-(?<{OldStart}>\d+),(?<{OldLines}>\d+) \+(?<{NewStart}>\d+),(?<{NewLines}>\d+) @@ (?<{MethodName}>(static)?( const )? [\w]+ [\w]+\([\w \*\,\t\n]*[\)\,])";
protected override string Extension => ".c";
protected override string ReservedFileName => "CReserved.txt";
public override MatchCollection GetMatches(string patchCode) {
......
......@@ -17,6 +17,7 @@ namespace VulnCrawler
var crawler = new T();
crawler.Init(dirPath);
var commits = crawler.Commits;
Console.WriteLine(commits.Count());
foreach (var commit in commits) {
// 커밋 메시지
string message = commit.Message;
......@@ -42,82 +43,99 @@ namespace VulnCrawler
foreach (var entry in entrys) {
// 기존 소스코드
var oldOid = entry.OldOid;
Blob oldBlob = self.Repository.Lookup<Blob>(oldOid);
string oldContent = oldBlob.GetContentText();
// 변경된 소스코드
var newOid = entry.Oid;
Blob newBlob = self.Repository.Lookup<Blob>(newOid);
string newContent = newBlob.GetContentText();
var regs = self.GetMatches(entry.Patch);
#region 패치 코드 출력
// 패치 전 코드 (oldContent)
// 패치 후 코드 (newContent)
// 패치 코드 (entry.Patch)
// 출력
//if (regs.Count > 0) {
// Console.BackgroundColor = ConsoleColor.DarkBlue;
// Console.WriteLine($"Old Content: \n{oldContent}");
// Console.ResetColor();
// Console.BackgroundColor = ConsoleColor.DarkMagenta;
// Console.WriteLine($"New Content: \n{newContent}");
// Console.ResetColor();
// Console.BackgroundColor = ConsoleColor.DarkRed;
// Console.WriteLine($"Patched: \n{entry.Patch}");
// Console.ResetColor();
// Console.WriteLine("-----------");
// Console.WriteLine(regs.Count);
//}
// 패치 코드에서 매칭된 파이썬 함수들로부터
// 패치 전 코드 파일(oldBlob)을 탐색하여 원본 파이썬 함수 가져오고(originalFunc)
//
#endregion
foreach (var reg in regs) {
var match = reg as Match;
string methodName = match.Groups[VulnAbstractCrawler.MethodName].Value;
string originalFunc, md5;
(originalFunc, md5) = self.Process(oldBlob.GetContentStream(),
match.Groups[VulnAbstractCrawler.MethodName].Value);
#region 현재 패치 엔트리 정보 출력(추가된 , 삭제된 , 패치 이전 경로, 패치 경로)
Console.ForegroundColor = ConsoleColor.Blue;
Console.WriteLine($"status: {entry.Status.ToString()}");
Console.WriteLine($"added: {entry.LinesAdded.ToString()}, deleted: {entry.LinesDeleted.ToString()}");
Console.WriteLine($"old path: {entry.OldPath.ToString()}, new path: {entry.Path.ToString()}");
Console.ResetColor();
Console.Write($"CVE: ");
Console.ForegroundColor = ConsoleColor.Red;
Console.Write($"{cve}");
Console.WriteLine("");
Console.ResetColor();
Console.ForegroundColor = ConsoleColor.Yellow;
Console.WriteLine($"Commit Message: {commitMsg}");
Console.ResetColor();
// 패치 전 원본 함수
Console.WriteLine($"Original Func: {originalFunc}");
// 해쉬 후
Console.WriteLine($"Original Func MD5: {md5}");
Console.BackgroundColor = ConsoleColor.DarkRed;
Console.WriteLine($"Patched: \n{entry.Patch}");
Console.ResetColor();
Console.WriteLine("==============================");
try
{
Blob oldBlob = self.Repository.Lookup<Blob>(oldOid);
string oldContent = oldBlob.GetContentText();
// 변경된 소스코드
var newOid = entry.Oid;
Blob newBlob = self.Repository.Lookup<Blob>(newOid);
string newContent = newBlob.GetContentText();
var regs = self.GetMatches(entry.Patch);
#region 패치 코드 출력
// 패치 전 코드 (oldContent)
// 패치 후 코드 (newContent)
// 패치 코드 (entry.Patch)
// 출력
if (regs.Count > 0)
{
// Console.BackgroundColor = ConsoleColor.DarkBlue;
// Console.WriteLine($"Old Content: \n{oldContent}");
// Console.ResetColor();
// Console.BackgroundColor = ConsoleColor.DarkMagenta;
// Console.WriteLine($"New Content: \n{newContent}");
// Console.ResetColor();
Console.ForegroundColor = ConsoleColor.Blue;
Console.WriteLine($"status: {entry.Status.ToString()}");
Console.WriteLine($"added: {entry.LinesAdded.ToString()}, deleted: {entry.LinesDeleted.ToString()}");
Console.WriteLine($"old path: {entry.OldPath.ToString()}, new path: {entry.Path.ToString()}");
Console.ResetColor();
Console.Write($"CVE: ");
Console.ForegroundColor = ConsoleColor.Red;
Console.Write($"{cve}");
Console.WriteLine("");
Console.ResetColor();
Console.ForegroundColor = ConsoleColor.Yellow;
Console.WriteLine($"Commit Message: {commitMsg}");
Console.ResetColor();
Console.BackgroundColor = ConsoleColor.DarkRed;
Console.WriteLine($"Patched: \n{entry.Patch}");
Console.ResetColor();
// Console.WriteLine("-----------");
}
// 패치 코드에서 매칭된 파이썬 함수들로부터
// 패치 전 코드 파일(oldBlob)을 탐색하여 원본 파이썬 함수 가져오고(originalFunc)
//
#endregion
foreach (var reg in regs)
{
var match = reg as Match;
string methodName = match.Groups[VulnAbstractCrawler.MethodName].Value.Trim();
Console.WriteLine("methodName = " + methodName);
string originalFunc, md5;
(originalFunc, md5) = self.Process(oldBlob.GetContentStream(),
match.Groups[VulnAbstractCrawler.MethodName].Value);
#region 현재 패치 엔트리 정보 출력(추가된 , 삭제된 , 패치 이전 경로, 패치 경로)
// 패치 전 원본 함수
Console.WriteLine($"Original Func: {originalFunc}");
// 해쉬 후
Console.WriteLine($"Original Func MD5: {md5}");
//Console.BackgroundColor = ConsoleColor.DarkRed;
//Console.WriteLine($"Patched: \n{entry.Patch}");
Console.ResetColor();
Console.WriteLine("==============================");
#endregion
}
}
catch (Exception)
{
continue;
}
}
}
......