1414using System . IO ;
1515using System . Linq ;
1616using System . Net ;
17+ using System . Security . Cryptography ;
18+ using System . Text ;
1719using System . Text . RegularExpressions ;
1820using System . Threading ;
1921
2022namespace Oxide . CSharp
2123{
2224 internal class CompilerService
2325 {
24- private const string baseUrl = "http://cdn .oxidemod.cloud/compiler /" ;
26+ private const string baseUrl = "http://downloads .oxidemod.dev/artifacts/Oxide.Compiler/develop /" ;
2527 private Hash < int , Compilation > compilations ;
2628 private Queue < CompilerMessage > messageQueue ;
2729 private Process process ;
@@ -548,11 +550,13 @@ private static bool DownloadFile(string url, string path, int retries = 3)
548550 {
549551 string fileName = Path . GetFileName ( path ) ;
550552 int retry = 0 ;
553+ string md5 = null ;
551554 try
552555 {
553556 DateTime ? last = null ;
554557 if ( File . Exists ( path ) )
555558 {
559+ md5 = GenerateFileHash ( path ) ;
556560 last = File . GetLastWriteTimeUtc ( path ) ;
557561 Log ( LogType . Info , $ "{ fileName } already exists, checking for updates. . .") ;
558562 }
@@ -564,7 +568,7 @@ private static bool DownloadFile(string url, string path, int retries = 3)
564568 byte [ ] data ;
565569 int code ;
566570 bool newerFound ;
567- if ( ! TryDownload ( url , retries , ref retry , last , out data , out code , out newerFound ) )
571+ if ( ! TryDownload ( url , retries , ref retry , last , out data , out code , out newerFound , ref md5 ) )
568572 {
569573 string attemptVerb = retries == 1 ? "attempt" : "attempts" ;
570574 Log ( LogType . Error , $ "Failed to download { fileName } after { retry } { attemptVerb } with response code '{ code } ', please manually download it from { url } and save it here { path } ") ;
@@ -582,6 +586,7 @@ private static bool DownloadFile(string url, string path, int retries = 3)
582586 {
583587 fs . Write ( data , 0 , data . Length ) ;
584588 }
589+
585590 Log ( LogType . Info , $ "Latest version of { fileName } has been downloaded") ;
586591 }
587592
@@ -594,7 +599,7 @@ private static bool DownloadFile(string url, string path, int retries = 3)
594599 }
595600 }
596601
597- private static bool TryDownload ( string url , int retries , ref int current , DateTime ? lastModified , out byte [ ] data , out int code , out bool newerFound )
602+ private static bool TryDownload ( string url , int retries , ref int current , DateTime ? lastModified , out byte [ ] data , out int code , out bool newerFound , ref string md5 )
598603 {
599604 newerFound = true ;
600605 data = null ;
@@ -604,7 +609,25 @@ private static bool TryDownload(string url, int retries, ref int current, DateTi
604609 HttpWebRequest request = ( HttpWebRequest ) WebRequest . Create ( url ) ;
605610 request . AllowAutoRedirect = true ;
606611
607- if ( lastModified . HasValue )
612+ if ( ! string . IsNullOrEmpty ( md5 ) )
613+ {
614+ int md5retries = 0 ;
615+ string servermd5 = null ;
616+ if ( TryDownload ( url + ".md5" , retries , ref md5retries , null , out byte [ ] md5data , out int md5code , out bool _ , ref servermd5 ) && md5code == 200 )
617+ {
618+ servermd5 = Encoding . UTF8 . GetString ( md5data ) . Trim ( ) ;
619+
620+ Log ( LogType . Info , $ "Local MD5: { md5 } Server MD5: { servermd5 } ") ;
621+
622+ if ( servermd5 . Equals ( md5 , StringComparison . InvariantCultureIgnoreCase ) )
623+ {
624+ Log ( LogType . Info , $ "MD5 of { url } matches local copy") ;
625+ newerFound = false ;
626+ return true ;
627+ }
628+ }
629+ }
630+ else if ( lastModified . HasValue )
608631 {
609632 request . IfModifiedSince = lastModified . Value ;
610633 }
@@ -626,13 +649,14 @@ private static bool TryDownload(string url, int retries, ref int current, DateTi
626649 {
627650 current ++ ;
628651 Thread . Sleep ( 1000 ) ;
629- return TryDownload ( url , retries , ref current , lastModified , out data , out code , out newerFound ) ;
652+ return TryDownload ( url , retries , ref current , lastModified , out data , out code , out newerFound , ref md5 ) ;
630653 }
631654 else
632655 {
633656 return false ;
634657 }
635658 }
659+
636660 MemoryStream fs = new MemoryStream ( ) ;
637661 Stream stream = response . GetResponseStream ( ) ;
638662 int bufferSize = 10000 ;
@@ -651,6 +675,7 @@ private static bool TryDownload(string url, int retries, ref int current, DateTi
651675 fs . Close ( ) ;
652676 stream . Close ( ) ;
653677 response . Close ( ) ;
678+
654679 return true ;
655680 }
656681 catch ( WebException webex )
@@ -669,7 +694,7 @@ private static bool TryDownload(string url, int retries, ref int current, DateTi
669694 {
670695 current ++ ;
671696 Thread . Sleep ( 1000 ) ;
672- return TryDownload ( url , retries , ref current , lastModified , out data , out code , out newerFound ) ;
697+ return TryDownload ( url , retries , ref current , lastModified , out data , out code , out newerFound , ref md5 ) ;
673698 }
674699 else
675700 {
@@ -693,5 +718,14 @@ private string GetCompilerVersion()
693718 FileVersionInfo version = FileVersionInfo . GetVersionInfo ( filePath ) ;
694719 return version . FileVersion ;
695720 }
721+
722+ private static string GenerateFileHash ( string file )
723+ {
724+ using ( MD5 md5 = MD5 . Create ( ) )
725+ using ( FileStream stream = File . OpenRead ( file ) )
726+ {
727+ return BitConverter . ToString ( md5 . ComputeHash ( stream ) ) . Replace ( "-" , string . Empty ) . ToLowerInvariant ( ) ;
728+ }
729+ }
696730 }
697731}
0 commit comments