PVS-Studio di Awan: Azure DevOps

Gambar 9

Ini adalah artikel kedua, yang berfokus pada penggunaan penganalisa PVS-Studio dalam sistem cloud CI. Kali ini kami akan mempertimbangkan platform Azure DevOps - solusi cloud CI \ CD dari Microsoft. Kami akan menganalisis proyek ShareX.

Kami membutuhkan tiga komponen. Yang pertama adalah analisa PVS-Studio. Yang kedua adalah Azure DevOps, yang akan kami integrasikan dengan analyzer. Yang ketiga adalah proyek yang akan kami periksa untuk menunjukkan kemampuan PVS-Studio saat bekerja di cloud. Jadi ayo pergi.

PVS-Studio adalah penganalisa kode statis untuk menemukan kesalahan dan cacat keamanan. Alat ini mendukung analisis kode C, C ++ dan C #.

Azure DevOps . Platform Azure DevOps mencakup alat-alat seperti Azure Pipeline, Azure Board, Azure Artifacts dan lainnya yang mempercepat proses pembuatan perangkat lunak dan meningkatkan kualitasnya.

ShareX adalah aplikasi gratis yang memungkinkan Anda menangkap dan merekam bagian mana pun dari layar. Proyek ini ditulis dalam C # dan sangat cocok untuk menunjukkan konfigurasi peluncuran analisa statis. Kode sumber proyek tersedia di GitHub .

Output dari perintah cloc untuk proyek ShareX:
Bahasa
file
kosong
komentar
Kode
C #
696
20658
24423
102565
Skrip MSBuild
11
1
77
5859
Dengan kata lain, proyek ini kecil, tetapi cukup memadai untuk menunjukkan karya PVS-Studio bersama dengan platform cloud.

Mari kita mulai konfigurasi


Untuk mulai bekerja di Azure DevOps, mari ikuti tautan dan tekan "Mulai gratis dengan GitHub".

Gambar 2

Berikan akses aplikasi Microsoft ke data akun GitHub.

Gambar 1

Anda harus membuat akun Microsoft untuk menyelesaikan pendaftaran Anda.

Gambar 12

Setelah mendaftar, buat proyek:

Gambar 5

Selanjutnya, kita perlu pindah ke "Pipeline" - "Builds" dan membuat pipeline Build baru.

Gambar 8

Ketika ditanya di mana kode kami berada, kami akan menjawab - GitHub.

Gambar 13

Otorisasi Azure Pipelines dan pilih repositori dengan proyek, yang untuknya kami akan mengkonfigurasi menjalankan penganalisa statis.

Gambar 7

Di jendela pemilihan templat, pilih "Starter pipeline."

Gambar 17

Kami dapat menjalankan analisis kode statis proyek dengan dua cara: menggunakan agen yang dihosting oleh Microsoft atau di-host sendiri.

Pertama, kami akan menggunakan agen yang dihosting oleh Microsoft. Agen tersebut adalah mesin virtual biasa yang diluncurkan ketika kami menjalankan pipa kami. Mereka dihapus ketika tugas selesai. Penggunaan agen tersebut memungkinkan kami untuk tidak membuang waktu untuk dukungan dan pembaruan mereka, tetapi memberlakukan batasan tertentu, misalnya - ketidakmampuan untuk menginstal perangkat lunak tambahan yang digunakan untuk membangun proyek.

Mari kita ganti konfigurasi default yang disarankan untuk yang berikut untuk menggunakan agen yang dihosting oleh Microsoft:

# Setting up run triggers # Run only for changes in the master branch trigger: - master # Since the installation of random software in virtual machines # is prohibited, we'll use a Docker container, # launched on a virtual machine with Windows Server 1803 pool: vmImage: 'win1803' container: microsoft/dotnet-framework:4.7.2-sdk-windowsservercore-1803 steps: # Download the analyzer distribution - task: PowerShell@2 inputs: targetType: 'inline' script: 'Invoke-WebRequest -Uri https://files.viva64.com/PVS-Studio_setup.exe -OutFile PVS-Studio_setup.exe' - task: CmdLine@2 inputs: workingDirectory: $(System.DefaultWorkingDirectory) script: | # Restore the project and download dependencies nuget restore .\ShareX.sln # Create the directory, where files with analyzer reports will be saved md .\PVSTestResults # Install the analyzer PVS-Studio_setup.exe /VERYSILENT /SUPPRESSMSGBOXES /NORESTART /COMPONENTS=Core # Create the file with configuration and license information "C:\Program Files (x86)\PVS-Studio\PVS-Studio_Cmd.exe" credentials -u $(PVS_USERNAME) -n $(PVS_KEY) # Run the static analyzer and convert the report in html. "C:\Program Files (x86)\PVS-Studio\PVS-Studio_Cmd.exe" -t .\ShareX.sln -o .\PVSTestResults\ShareX.plog "C:\Program Files (x86)\PVS-Studio\PlogConverter.exe" -t html -o .\PVSTestResults\ .\PVSTestResults\ShareX.plog # Save analyzer reports - task: PublishBuildArtifacts@1 inputs: pathToPublish: PVSTestResults artifactName: PVSTestResults 

Catatan: menurut dokumentasi , wadah yang digunakan harus di-cache dalam gambar mesin virtual, tetapi pada saat penulisan artikel itu tidak berfungsi dan wadah diunduh setiap kali tugas dimulai, yang berdampak negatif pada waktu eksekusi.

Mari kita simpan pipeline dan buat variabel yang akan digunakan untuk membuat file lisensi. Untuk melakukan ini, buka jendela edit pipa dan klik "Variabel" di sudut kanan atas.

Gambar 14

Kemudian, tambahkan dua variabel - PVS_USERNAME dan PVS_KEY , masing-masing berisi nama pengguna dan kunci lisensi. Saat membuat variabel PVS_KEY jangan lupa untuk memilih "Rahasiakan nilai ini" untuk mengenkripsi nilai variabel dengan kunci RSA 2048-bit dan untuk menekan output dari nilai variabel dalam log kinerja tugas.

Gambar 15

Simpan variabel dan jalankan pipeline dengan mengklik "Run".

Opsi kedua untuk menjalankan analisis - gunakan agen yang di-host-sendiri. Kami dapat menyesuaikan dan mengelola sendiri agen yang dihosting sendiri. Agen tersebut memberikan lebih banyak peluang untuk menginstal perangkat lunak, yang diperlukan untuk membangun dan menguji produk perangkat lunak kami.

Sebelum menggunakan agen tersebut, Anda harus mengonfigurasinya sesuai dengan instruksi dan menginstal dan mengkonfigurasi analisa statis.

Untuk menjalankan tugas pada agen yang di-host-sendiri, kami akan mengganti konfigurasi yang disarankan dengan yang berikut:

 # Setting up triggers # Run the analysis for master-branch trigger: - master # The task is run on a self-hosted agent from the pool 'MyPool' pool: 'MyPool' steps: - task: CmdLine@2 inputs: workingDirectory: $(System.DefaultWorkingDirectory) script: | # Restore the project and download dependencies nuget restore .\ShareX.sln # Create the directory where files with analyzer reports will be saved md .\PVSTestResults # Run the static analyzer and convert the report in html. "C:\Program Files (x86)\PVS-Studio\PVS-Studio_Cmd.exe" -t .\ShareX.sln -o .\PVSTestResults\ShareX.plog "C:\Program Files (x86)\PVS-Studio\PlogConverter.exe" -t html -o .\PVSTestResults\ .\PVSTestResults\ShareX.plog # Save analyzer reports - task: PublishBuildArtifacts@1 inputs: pathToPublish: PVSTestResults artifactName: PVSTestResults 

Setelah tugas selesai, Anda dapat mengunduh arsip dengan laporan penganalisa di bawah tab "Ringkasan" atau Anda dapat menggunakan ekstensi Kirim Email yang memungkinkan untuk mengonfigurasi email atau mempertimbangkan alat lain yang nyaman di Marketplace .

Gambar 21

Hasil analisis


Sekarang mari kita lihat beberapa bug yang ditemukan di proyek yang diuji, ShareX.

Pemeriksaan berlebihan

Untuk melakukan pemanasan, mari kita mulai dengan kelemahan sederhana dalam kode, yaitu, dengan pemeriksaan berlebihan:

 private void PbThumbnail_MouseMove(object sender, MouseEventArgs e) { .... IDataObject dataObject = new DataObject(DataFormats.FileDrop, new string[] { Task.Info.FilePath }); if (dataObject != null) { Program.MainForm.AllowDrop = false; dragBoxFromMouseDown = Rectangle.Empty; pbThumbnail.DoDragDrop(dataObject, DragDropEffects.Copy | DragDropEffects.Move); Program.MainForm.AllowDrop = true; } .... } 

Peringatan PVS-Studio: V3022 [CWE-571] Ekspresi 'dataObject! = Null' selalu benar. TaskThumbnailPanel.cs 415

Mari kita perhatikan pemeriksaan variabel dataObject untuk null . Kenapa disini? dataObject tidak boleh nol dalam kasus ini, karena ini diinisialisasi dengan referensi pada objek yang dibuat. Akibatnya, kami melakukan pemeriksaan berlebihan. Kritis? Tidak. Tampak ringkas? Tidak. Pemeriksaan ini jelas lebih baik dihapus agar tidak mengacaukan kode.

Mari kita lihat fragmen kode lain yang bisa kita komentari dengan cara yang sama:

 private static Image GetDIBImage(MemoryStream ms) { .... try { .... return new Bitmap(bmp); .... } finally { if (gcHandle != IntPtr.Zero) { GCHandle.FromIntPtr(gcHandle).Free(); } } .... } private static Image GetImageAlternative() { .... using (MemoryStream ms = dataObject.GetData(format) as MemoryStream) { if (ms != null) { try { Image img = GetDIBImage(ms); if (img != null) { return img; } } catch (Exception e) { DebugHelper.WriteException(e); } } } .... } 

Peringatan PVS-Studio: V3022 [CWE-571] Ekspresi 'img! = Null' selalu benar. ClipboardHelpers.cs 289

Dalam metode GetImageAlternative , variabel img diperiksa bahwa itu bukan nol tepat setelah instance baru dari kelas Bitmap dibuat. Perbedaan dari contoh sebelumnya di sini adalah bahwa kita menggunakan metode GetDIBImage alih-alih konstruktor untuk menginisialisasi variabel img . Penulis kode menyarankan bahwa pengecualian mungkin terjadi dalam metode ini, tetapi ia menyatakan hanya blok yang mencoba dan akhirnya , menghilangkan tangkapan . Oleh karena itu, jika pengecualian terjadi, metode pemanggil GetImageAlternative tidak akan mendapatkan referensi ke objek dari tipe Bitmap , tetapi harus menangani pengecualian di blok tangkapnya sendiri. Dalam hal ini, variabel img tidak akan diinisialisasi dan utas eksekusi bahkan tidak akan mencapai img! = Cek kosong tetapi akan masuk ke blok tangkap. Akibatnya, penganalisa memang menunjuk ke pemeriksaan yang berlebihan.

Mari kita perhatikan contoh peringatan V3022 berikut :

 private void btnCopyLink_Click(object sender, EventArgs e) { .... if (lvClipboardFormats.SelectedItems.Count == 0) { url = lvClipboardFormats.Items[0].SubItems[1].Text; } else if (lvClipboardFormats.SelectedItems.Count > 0) { url = lvClipboardFormats.SelectedItems[0].SubItems[1].Text; } .... } 

Peringatan PVS-Studio: V3022 [CWE-571] Ekspresi 'lvClipboardFormats.SelectedItems.Count> 0' selalu benar. AfterUploadForm.cs 155

Mari kita lihat lebih dekat ekspresi kondisional kedua. Di sana kami memeriksa nilai properti Hitung baca-saja. Properti ini menunjukkan jumlah elemen dalam instance koleksi SelectedItems . Kondisi ini hanya dijalankan jika properti Count lebih besar dari nol. Itu semua akan baik-baik saja, tetapi di eksternal jika pernyataan Count sudah diperiksa untuk 0. Contoh koleksi SelectedItems tidak dapat memiliki jumlah elemen kurang dari nol, oleh karena itu, Hitungan sama atau lebih besar dari 0. Karena kita sudah sudah melakukan pemeriksaan Count untuk 0 di pernyataan if pertama dan itu salah, tidak ada gunanya untuk menulis cek Count lebih besar dari nol di cabang lain.

Contoh terakhir dari peringatan V3022 adalah potongan kode berikut:

 private void DrawCursorGraphics(Graphics g) { .... int cursorOffsetX = 10, cursorOffsetY = 10, itemGap = 10, itemCount = 0; Size totalSize = Size.Empty; int magnifierPosition = 0; Bitmap magnifier = null; if (Options.ShowMagnifier) { if (itemCount > 0) totalSize.Height += itemGap; .... } .... } 

Peringatan PVS-Studio: Ekspresi V3022 'itemCount> 0' selalu salah. RegionCaptureForm.cs 1100

Penganalisis memperhatikan bahwa itemCount kondisi > 0 akan selalu salah, karena variabel itemCount dideklarasikan dan pada saat yang sama ditetapkan nol di atas. Variabel ini tidak digunakan di mana pun hingga kondisi tersebut, oleh karena itu penganalisa benar tentang ekspresi kondisional, yang nilainya selalu salah.

Baiklah, sekarang mari kita lihat sesuatu yang benar-benar ganjil.

Cara terbaik untuk memahami bug adalah memvisualisasikan bug

Sepertinya kami menemukan kesalahan yang agak menarik di tempat ini:

 public static void Pixelate(Bitmap bmp, int pixelSize) { .... float r = 0, g = 0, b = 0, a = 0; float weightedCount = 0; for (int y2 = y; y2 < yLimit; y2++) { for (int x2 = x; x2 < xLimit; x2++) { ColorBgra color = unsafeBitmap.GetPixel(x2, y2); float pixelWeight = color.Alpha / 255; r += color.Red * pixelWeight; g += color.Green * pixelWeight; b += color.Blue * pixelWeight; a += color.Alpha * pixelWeight; weightedCount += pixelWeight; } } .... ColorBgra averageColor = new ColorBgra((byte)(b / weightedCount), (byte)(g / weightedCount), (byte)(r / weightedCount), (byte)(a / pixelCount)); .... } 

Saya tidak ingin menunjukkan semua kartu dan mengungkapkan apa yang ditemukan oleh analis kami, jadi mari kita kesampingkan sebentar.

Dengan nama metode, mudah untuk menebak apa yang dilakukannya - Anda memberikannya gambar atau potongan gambar, dan itu menggandakannya. Kode metode ini cukup panjang, jadi kami tidak akan mengutipnya sepenuhnya, tetapi coba jelaskan algoritmanya dan jelaskan bug apa yang berhasil ditemukan oleh PVS-Studio.

Metode ini menerima dua parameter: objek jenis Bitmap dan nilai tipe int yang menunjukkan ukuran pikselasi. Algoritma operasi cukup sederhana:

1) Bagi fragmen gambar yang diterima ke dalam kotak dengan sisi sama dengan ukuran pixelation. Misalnya, jika kita memiliki ukuran pixelation sama dengan 15, kita akan mendapatkan kotak, berisi 15x15 = 225 piksel.

2) Selanjutnya, kami melintasi setiap piksel dalam kuadrat ini dan mengakumulasikan nilai bidang Merah , Hijau , Biru dan Alpha dalam variabel perantara, dan sebelum itu gandakan nilai warna yang sesuai dan saluran alfa dengan variabel pixelWeight , yang diperoleh oleh membagi nilai Alpha dengan 255 (variabel Alpha adalah tipe byte ). Juga ketika melintasi piksel, kami menjumlahkan nilai-nilai, ditulis dalam pixelWeight ke dalam variabel WeightedCount . Fragmen kode yang mengeksekusi tindakan di atas adalah sebagai berikut:

 ColorBgra color = unsafeBitmap.GetPixel(x2, y2); float pixelWeight = color.Alpha / 255; r += color.Red * pixelWeight; g += color.Green * pixelWeight; b += color.Blue * pixelWeight; a += color.Alpha * pixelWeight; weightedCount += pixelWeight; 

Omong-omong, perhatikan bahwa jika nilai variabel Alpha adalah nol, pixelWeight tidak akan menambah variabel WeightedCount nilai apa pun untuk piksel ini. Kami akan membutuhkannya di masa depan.

3) Setelah melintasi semua piksel dalam kuadrat saat ini, kami dapat membuat warna "rata-rata" yang umum untuk kuadrat ini. Kode melakukan ini terlihat sebagai berikut:

 ColorBgra averageColor = new ColorBgra((byte)(b / weightedCount), (byte)(g / weightedCount), (byte)(r / weightedCount), (byte)(a / pixelCount)); 

4) Sekarang ketika kita mendapatkan warna akhir dan menuliskannya dalam variabel averageColor , kita dapat kembali melintasi setiap piksel persegi dan memberikan nilai dari averageColor .

5) Kembali ke poin 2 sementara kami memiliki kotak tidak tertangani.

Sekali lagi, variabel weightedCount tidak sama dengan jumlah semua piksel dalam kuadrat. Misalnya, jika gambar berisi piksel yang benar-benar transparan (nilai nol dalam saluran alfa), variabel pixelWeight akan menjadi nol untuk piksel ini ( 0/255 = 0). Oleh karena itu, piksel ini tidak akan memengaruhi pembentukan variabel WeightedCount . Ini cukup logis - tidak ada gunanya memperhitungkan warna akun piksel yang benar-benar transparan.

Jadi semuanya masuk akal - pixelation harus bekerja dengan benar. Dan itu benar-benar terjadi. Itu tidak untuk gambar png yang menyertakan piksel dengan nilai di saluran alpha di bawah 255 dan tidak sama dengan nol. Perhatikan gambar pixelated di bawah ini:

Gambar 3

Sudahkah Anda melihat pixelation? Kami juga tidak. Oke, sekarang mari kita ungkapkan intrik kecil ini dan jelaskan di mana tepatnya bug itu bersembunyi di metode ini. Kesalahan merayap ke baris perhitungan variabel pixelWeight :

 float pixelWeight = color.Alpha / 255; 

Faktanya adalah bahwa ketika mendeklarasikan variabel pixelWeight sebagai float , pembuat kode menyiratkan bahwa ketika membagi bidang Alpha dengan 255, ia akan mendapatkan angka fraksional selain nol dan satu. Di sinilah masalahnya, karena variabel Alpha adalah tipe byte . Saat menyelam dengan 255, kami mendapatkan nilai integer. Hanya setelah itu akan secara implisit dilemparkan ke tipe float , yang berarti bahwa bagian pecahan hilang.

Sangat mudah untuk menjelaskan mengapa tidak mungkin untuk pixelate gambar png dengan transparansi. Karena untuk nilai piksel saluran alpha berada dalam kisaran 0 <Alpha <255, variabel Alpha dibagi dengan 255 akan selalu menghasilkan 0. Oleh karena itu, nilai variabel pixelBerat , r , g , b , a , WeightedCount juga akan selalu menjadi 0. Sebagai hasilnya, rata-rata Warna kami akan dengan nilai nol di semua saluran: merah - 0, biru - 0, hijau - 0, alfa - 0. Dengan mengecat kotak dalam warna ini, kami tidak mengubah warna asli piksel, karena rata-rata Warna benar-benar transparan. Untuk memperbaiki kesalahan ini, kita hanya perlu secara eksplisit melemparkan bidang Alpha ke tipe float . Versi tetap dari baris kode mungkin terlihat seperti ini:

 float pixelWeight = (float)color.Alpha / 255; 

Nah, sudah saatnya mengutip pesan PVS-Studio untuk kode yang salah:

Peringatan PVS-Studio: V3041 [CWE-682] Ungkapan itu secara implisit dilemparkan dari tipe 'int' ke tipe 'float'. Pertimbangkan untuk menggunakan pemeran tipe eksplisit untuk menghindari hilangnya bagian fraksional. Contoh: double A = (double) (X) / Y; ImageHelpers.cs 1119

Sebagai perbandingan, mari kita kutip tangkapan layar dari gambar yang benar-benar pixelated, diperoleh pada versi aplikasi yang diperbaiki:

Gambar 6

Potensi NullReferenceException

 public static bool AddMetadata(Image img, int id, string text) { .... pi.Value = bytesText; if (pi != null) { img.SetPropertyItem(pi); return true; } .... } 

Peringatan PVS-Studio: V3095 [CWE-476] Objek 'pi' digunakan sebelum diverifikasi terhadap null. Periksa baris: 801, 803. ImageHelpers.cs 801

Fragmen kode ini menunjukkan bahwa penulis berharap bahwa variabel pi dapat menjadi nol , itu sebabnya sebelum memanggil metode SetPropertyItem , centang pi! = Null terjadi. Sungguh aneh bahwa sebelum pemeriksaan ini properti diberi array byte, karena jika pi nol , pengecualian dari tipe NullReferenceException akan dibuang.

Situasi serupa telah terjadi di tempat lain:

 private static void Task_TaskCompleted(WorkerTask task) { .... task.KeepImage = false; if (task != null) { if (task.RequestSettingUpdate) { Program.MainForm.UpdateCheckStates(); } .... } .... } 

Peringatan PVS-Studio: V3095 [CWE-476] Objek 'tugas' digunakan sebelum diverifikasi terhadap nol. Periksa baris: 268, 270. TaskManager.cs 268

PVS-Studio menemukan kesalahan serupa lainnya. Intinya sama, jadi tidak ada kebutuhan besar untuk mengutip fragmen kode, pesan analisa akan cukup.

Peringatan PVS-Studio: V3095 [CWE-476] Objek 'Config.PhotobucketAccountInfo' digunakan sebelum diverifikasi dengan null. Periksa baris: 216, 219. UploadersConfigForm.cs 216

Nilai pengembalian yang sama

Fragmen kode yang mencurigakan ditemukan dalam metode EvalWindows dari kelas WindowsList , yang mengembalikan true dalam semua kasus:

 public class WindowsList { public List<IntPtr> IgnoreWindows { get; set; } .... public WindowsList() { IgnoreWindows = new List<IntPtr>(); } public WindowsList(IntPtr ignoreWindow) : this() { IgnoreWindows.Add(ignoreWindow); } .... private bool EvalWindows(IntPtr hWnd, IntPtr lParam) { if (IgnoreWindows.Any(window => hWnd == window)) { return true; // <= } windows.Add(new WindowInfo(hWnd)); return true; // <= } } 

Peringatan PVS-Studio: V3009 Aneh bahwa metode ini selalu mengembalikan satu dan nilai 'benar' yang sama. WindowsList.cs 82

Di tampak logis bahwa jika dalam daftar bernama IgnoreWindows ada pointer dengan nama yang sama dengan hWnd , metode tersebut harus mengembalikan false .

Daftar IgnoreWindows dapat diisi baik ketika memanggil konstruktor WindowsList (IntPtr ignWindow) atau langsung melalui mengakses properti sebagai milik umum. Lagi pula, menurut Visual Studio, saat ini dalam kode daftar ini tidak diisi. Ini adalah tempat aneh lain dari metode ini.

Panggilan penangan acara yang tidak aman

 protected void OnNewsLoaded() { if (NewsLoaded != null) { NewsLoaded(this, EventArgs.Empty); } } 

Peringatan PVS-Studio: V3083 [CWE-367] Doa yang tidak aman dari acara 'NewsLoaded', NullReferenceException dimungkinkan. Pertimbangkan menugaskan acara ke variabel lokal sebelum menjalankannya. NewsListControl.cs 111

Di sini kasus yang sangat buruk mungkin terjadi. Setelah memeriksa variabel NewsLoaded untuk null, metode yang menangani acara, dapat berhenti berlangganan, misalnya, di utas lain. Dalam hal ini, pada saat kita masuk ke tubuh pernyataan if, variabel NewsLoaded akan menjadi nol. NullReferenceException mungkin terjadi ketika mencoba memanggil pelanggan dari acara NewsLoaded , yang nol. Jauh lebih aman menggunakan operator bersyarat nol dan menulis ulang kode di atas sebagai berikut:

 protected void OnNewsLoaded() { NewsLoaded?.Invoke(this, EventArgs.Empty); } 

Alat analisis menunjuk 68 fragmen yang serupa. Kami tidak akan menjelaskan semuanya - mereka semua memiliki pola panggilan yang sama.

Kembalikan null dari ToString

Baru-baru ini saya menemukan dari artikel yang menarik dari rekan saya bahwa Microsoft tidak merekomendasikan pengembalian nol dari metode ToString yang ditimpa. PVS-Studio sangat menyadari hal ini:

 public override string ToString() { lock (loggerLock) { if (sbMessages != null && sbMessages.Length > 0) { return sbMessages.ToString(); } return null; } } 

Peringatan PVS-Studio: V3108 Tidak disarankan untuk mengembalikan 'null' dari metode 'ToSting ()'. Logger.cs 167

Kenapa ditugaskan jika tidak digunakan?

 public SeafileCheckAccInfoResponse GetAccountInfo() { string url = URLHelpers.FixPrefix(APIURL); url = URLHelpers.CombineURL(APIURL, "account/info/?format=json"); .... } 

Peringatan PVS-Studio: V3008 Variabel 'url' diberi nilai dua kali berturut-turut. Mungkin ini sebuah kesalahan. Periksa baris: 197, 196. Seafile.cs 197

Seperti yang dapat kita lihat dari contoh, ketika mendeklarasikan variabel url , ia diberi nilai, dikembalikan dari metode FixPrefix . Di baris berikutnya, kami menghapus nilai yang diperoleh bahkan tanpa menggunakannya di mana pun. Kami mendapatkan sesuatu yang mirip dengan kode mati: itu berfungsi, tetapi tidak mempengaruhi hasilnya. Kemungkinan besar, kesalahan ini adalah hasil dari copy-paste, karena fragmen kode tersebut terjadi di 9 metode lainnya. Sebagai contoh, kami akan mengutip dua metode dengan baris pertama yang serupa:

 public bool CheckAuthToken() { string url = URLHelpers.FixPrefix(APIURL); url = URLHelpers.CombineURL(APIURL, "auth/ping/?format=json"); .... } .... public bool CheckAPIURL() { string url = URLHelpers.FixPrefix(APIURL); url = URLHelpers.CombineURL(APIURL, "ping/?format=json"); .... } 

Kesimpulan


Seperti yang dapat kita lihat, kompleksitas konfigurasi pemeriksaan penganalisis otomatis tidak bergantung pada sistem CI yang dipilih. Kami benar-benar membutuhkan 15 menit dan beberapa klik mouse untuk mengonfigurasi pemeriksaan kode proyek kami dengan penganalisa statis.

Sebagai kesimpulan, kami mengundang Anda untuk mengunduh dan mencoba penganalisa pada proyek Anda.

Source: https://habr.com/ru/post/id467357/


All Articles