تحلیل ایستای کد، تکنیک شناخت تقریبی از رفتار زمان اجرای یک برنامه است. به عبارت دیگر، این فرآیند پیشبینی خروجی یک برنامه، بدون اجرای واقعی است. با این حال، اخیراً، اصطلاح "تحلیل ایستای کد" بیشتر اشاره به یکی از کاربردهای این تکنیک یعنی درک برنامه و تشخیص مسائل استفاده میشود. این تحلیل و درک برنامه، باگهای احتمالی عملکرد، حفرههای امنیتی و غیره را کاهش می دهد. این همان استفادهای است که در طول این پست به آن اشاره می کنیم.
پالایش تکنیکها برای کشف سریع خطا مانند سایر روشها به عنوان نشانهای از دید ما از علم است.
- جی رابرت اوپنهایمر
رویکردها و ابزارهای مختلفی در زمینه تحلیل ایستای کد استفاده میشود که هر کدام دارای مزایا و معایبی هستند که تأثیر مستقیمی بر کیفیت بازخورد ارزیابی دارند. در این پست، رویکردهای اصلی مختلف و ابزارهای مختلف برای تحلیل ایستای کد، ارزیابی و مقایسه شده است.
استفاده از روشهای تحلیلی برای بررسی کد به منظور تصحیح اشکالات پیاده سازی، یکی از ستونهای اصلی توسعه نرمافزار است. در ابتدای پیدایش صنعت نرمافزار هیچ درکی در مورد اینکه بررسی کد چقدر ضروری و مؤثر است وجود نداشت، اما در دهه 1970، بررسی و بازرسی رسمی برای بهره وری و کیفیت محصول مهم شناخته شد. تعریف فاگان از کارایی تشخیص خطا به شرح زیر است:
بنابراین، تشخیص خطا تا آنجا که به کد مربوط میشود، به نفع برنامه نویس است که از تجزیه و تحلیل استاتیک استفاده کند. اگرچه این بدان معنا نیست که دیگر روشهای تجزیه و تحلیل نرمافزار استفاده نکرد؛ برعکس، بهترین راه برای تأیید اینکه یک پیاده سازی دارای کمترین خطا یا نقص است، ترکیب معیارهای استاتیک و پویا تجزیه و تحلیل است.
رویکرد تحلیل ایستا به منظور بررسی کد، بررسی انطباق قوانین خاص، استفاده از آرگومانها و غیره است. رویکرد پویا اساساً اجرای کد و اجرای برنامه است. این بدان معنی است که آزمون و بررسی کد چیزهای جداگانه و قابل تشخیصی هستند، اما توصیه نمیشود که یکی بدون دیگری اتفاق بیفتد. هدف ما بر شرح روشهای تحلیل استاتیک، با توجه ویژه به ابزارهای موجود در بازار که این نوع خدمات را ارائه میکنند، تمرکز دارد.
تحلیل ایستای کد، آنالیز نرم افزارهای کامپیوتری است که بدون اجرای واقعی برنامههای ساخته شده از آن نرم افزار، انجام میشود. میتوان استدلال کرد که معیارهای نرم افزار و مهندسی معکوس اشکالی از تجزیه و تحلیل استاتیک هستند. برنامه نویسان همیشه اشتباهات کوچکی انجام میدهند، مانند یک نقطه ویرگول در اینجا، یک پرانتز اضافی در آنجا، و غیره. اغلب اوقات این گافها بی اهمیت هستند، کامپایلر خطا را یادداشت میکند، برنامه نویس کد را اصلاح میکند و روند توسعه ادامه مییابد. با این حال، این چرخه سریع بازخورد و پاسخ معمولاً در مورد بیشتر آسیبپذیریهای امنیتی اعمال نمیشود، زیرا میتوانند برای مدت زمان نامحدودی قبل از کشف غیرفعال باشند. همانطور که میدانید، هر چه یک نقص در نرمافزار مدت طولانیتری غیرفعال باشد، هزینه تعمیر آن بیشتر میشود.
وعده تجزیه و تحلیل استاتیک این است که بسیاری از مشکلات رایج کدگذاری را به طور خودکار قبل از انتشار یک برنامه شناسایی کنید. هدف تجزیه و تحلیل استاتیک، بررسی متن یک برنامه به صورت ایستا، بدون تلاش برای اجرای آن است.
بررسی دستی شکلی از تجزیه و تحلیل ایستا است که بسیار زمان بر است، و برای اجرای موثر آن، حسابرسان کد انسانی ابتدا باید بدانند که چه نوع خطاهایی قرار است پیدا کنند تا بتوانند به طور دقیق کد را بررسی کنند. بررسی کد برنامه در هر مرحله از توسعه نرم افزار قابل انجام است، اما بهترین نتایج زمانی حاصل می شود که این کار در مراحل اولیه انجام شود زیرا شناسایی و تصحیح آسیب پذیریهای امنیتی و نقصهای کیفیت در اواخر فرآیند توسعه نرمافزار، هزینه سنگینی دارد. هنگامی که این اشکالات به بازار انشتار پیدا میکنند و توسط مشتریان کشف شوند، عواقب آن میتواند بر قیمت نهایی تأثیر بگذارد و به شهرت آسیب برساند.
بازبینی نه تنها شامل کدها میشود، بلکه شامل تمام اسناد، الزامات و طرحهایی است که توسعهدهنده تولید میکند، همه چیز مستعد بررسی است زیرا ممکن است در هر مرحله از توسعه نرمافزار خطاهایی پنهان باشد. در تصویر زیر، فاز اولیه بررسی دستی را نشان میدهد که مروری بر خود کد نوشته شده است، که در آن برنامه نویس سعی میکند خود کدی را که پیاده سازی کرده است ارزیابی و تصحیح کند. این راهنما بر ارائه کد مورد نظر توسط برنامه نویس خود به مخاطبان متمرکز است. بررسی همتا زمانی است که برنامه نویس کد خود را برای بررسی به همکار خود ارائه میدهد. در نهایت، بازرسی و حسابرسی، که معمولا توسط شخص ثالثی انجام میشود، حسابرسی بالاترین بررسی رسمی است.
بهترین راه برای شناسایی و تصحیح باگها در مرحلهای است که خود برنامه نویس بررسی را انجام میدهد و سعی میکند مشکلات موجود در کد خود را پیدا و تصحیح کند، این معمولا به عنوان خود بازبینی شناخته میشود. هر برنامه نویس باید احساس مسئولیت شخصی در قبال پیاده سازیهای خود داشته باشد.
فرآیند بررسی تیمی میتواند کمی پیچیده تر باشد و چندین مرحله مختلف در بررسی نرمافزار وجود دارد. یک روش جالب این است که در آن توسعهدهنده، کد و ایدههای خود را برای مخاطب توضیح میدهد و در معرض انتقاد آنها قرار میگیرد. علاوه بر این، الزامات رسمی برای انجام بررسی های ایستا کد وجود دارد. اجزای یک بازنگری رسمی عبارتند از: اهداف بازبینی، مجموعه موارد در حال بررسی، مجموعهای از پیش شرطها برای بررسی، نقشها، اندازه تیم، شرکت کنندگان، چک لیستها، معیارها و روشهای کار مجدد.
ابزارهای تحلیل ایستا نسبت به بررسیهای دستی بسیار مطلوب هستند زیرا سریعتر هستند، به این معنی که میتوانند برنامهها را به دفعات ارزیابی کنند. همانطور که یک برنامه نویس میتواند به یک کامپایلر تکیه کند تا به طور مداوم نکات ظریف نحو زبان را اعمال کند، یک ابزار تحلیل ایستا نیز خوب میتواند نکات دقیقی از باگهای پیچیدهتر بیابد. علاوه بر این، آزمون خطاهایی مانند آسیبپذیریهای امنیتی پیچیده است، زیرا اغلب در حالتهای صعب العبور یا در شرایط غیرعادی ظاهر میشوند. ابزارهای تجزیه و تحلیل ایستا میتوانند در گوشههای تاریک برنامه نیز تحلیل خود را انجام دهند.
باید کار کردن از ابزارهای تحلیل ایستا آسان باشند، این بدان معناست که نتایج آنها باید برای توسعه دهندگان عادی که ممکن است اطلاعات زیادی در مورد امنیت نداشته باشند قابل درک باشد و کاربران خود را در مورد برنامه نویسی خوب آموزش دهند. یکی دیگر از ویژگیهای مهم، نوع دانش (مجموعه قوانین) است که ابزار اعمال میکند. دقت داشته باشید که ابزارهای تجزیه و تحلیل ایستا نمیتوانند همه مشکلات امنیتی را حل کنند، عمدتاً به این دلیل که این ابزارها به دنبال مجموعه ثابتی از الگوها یا قوانین در کد هستند. اگرچه ابزارهای پیشرفتهتر اجازه میدهند قوانین جدیدی در طول زمان اضافه شوند، اما اگر هنوز قانونی برای یافتن یک مشکل خاص نوشته نشده باشد، ابزار هرگز آن مشکل را پیدا نمیکند.
خروجی ابزارهای تحلیل ایستا هنوز نیاز به ارزیابی انسانی دارد. بنابراین هیچ راهی برای اجتناب از مطالعه خروجی و قضاوت در مورد اینکه کدام مسائل باید برطرف شوند و کدام یک سطح قابل قبولی از برنامه نویس را نشان میدهند وجود ندارد. توجه داشته باشید که یک ابزار همچنین میتواند منفیهای کاذب تولید کند (برنامه حاوی اشکالاتی است که ابزار گزارش نمیکند) یا مثبت کاذب (ابزار اشکالاتی را گزارش میکند که برنامه حاوی آنها نیست). مثبتهای کاذب به دلیل زمانی که توسعهدهنده متوجه میشود هیچ خطایی وجود ندارد، مشکل ایجاد میکند، اما منفیهای کاذب بسیار خطرناکتر هستند، زیرا منجر به احساس امنیت کاذب میشوند. یک ابزار خوب برای تجزیه و تحلیل ایستا ابزاری است که اگرچه گاهی اوقات مثبت کاذب را نشان میدهد، اما هرگز اجازه نمیدهد یک منفی کاذب عبور کند.
آزمون یک برنامه دارای نکات بسیار زیادی است تا بتوان آن را مطابق با مشخصات تعیین شده، در نظر گرفت. تجزیه و تحلیل ایستا تنها در صورتی میتواند معنا پیدا کند که سایر اشکال تجزیه و تحلیل ساخته شوند، زیرا هیچ کس فقط نمیتواند از این تکنیک استفاده کند و مطمئن باشد که نرم افزار بدون عیب است، که این میتواند به عنوان یک نقطه ضعف بزرگ تلقی شود. از سوی دیگر، هیچ راهی برای اطمینان از اینکه پیاده سازی بدون خطا است وجود ندارد.
اساساً دو نوع تحلیل نرم افزار وجود دارد: پویا و ایستا. همانطور که در ابتدا توضیح داده شد، تجزیه و تحلیل ایستا بدون اجرای واقعی برنامههای ساخته شده انجام میشود، اما تحلیل پویا با اجرای برنامهها بر روی یک پردازنده واقعی یا مجازی انجام میشود. اگرچه تجزیه و تحلیل پویا الزامات عملکردی یک پروژه نرم افزاری را بررسی میکند، تجزیه و تحلیل ایستا می تواند میزان تست و اشکال زدایی لازم برای آماده شدن نرم افزار را کاهش دهد.
نقطه ضعف تجزیه و تحلیل پویا این است که نتایج تولید شده برای اجرای آتی تعمیم داده نمیشوند. هیچ اطمینانی وجود ندارد که مجموعه ورودیها، مشخصه همه اجرای برنامههای ممکن باشد. برنامههایی که به ورودیهای صحیح نیاز دارند نمیتوانند از نتایج یک تحلیل پویای معمولی استفاده کنند، همانطور که برنامههایی که به ورودیهای دقیق نیاز دارند قادر به استفاده از نتایج یک تحلیل ایستا معمولی نیستند
برخی از آنالیزهای ایستا بسیار سریع اجرا میشوند، اما به طور کلی، به دست آوردن نتایج دقیق به مقدار زیادی محاسبات و انتظارهای طولانی نیاز دارد، به خصوص هنگام تجزیه و تحلیل برنامههای بزرگ. به طور معمول، تجزیه و تحلیل ایستا محافظه کارانه و صحیح است. طراحی نرم افزار همچنین مستعد وجود اشتباهاتی است، تشخیص این مشکلات از طریق آزمون دشوار است، بیشتر به این دلیل که منشأ اکثر مشکلات در نیازها و طراحی نرم افزار است. الزامات و مصنوعات طراحی را میتوان بررسی کرد اما قابل اجرا و آزمون نیست. از سوی دیگر، به دلیل سازماندهی ضعیف و ساختار نامناسب کد، یافتن مشکلات مربوط به طراحی یا مشکلات توسعه کد کند و غیرممکن است.
یکی از مزایای رویکرد تجزیه و تحلیل ایستا در طول توسعه این است که کد به شدت به گونهای هدایت میشود که قابل اعتماد و خوانا باشد. این همچنین بر تأیید کد پس از آماده شدن تأثیر میگذارد و تعداد مشکلات موجود در اجرای بعدی آن کد را کاهش می دهد.
ابزارهایی مبتنی بر تحلیل ایستا را میتوان برای کشف نقص در برنامهها استفاده کرد. چندین ابزار در طول سالها به منظور کمک به این فرآیند توسعه یافته است. ابزارها بر اساس تجزیه و تحلیل ایستا ساخته شدهاند و میتوانند برای یافتن خطاها و حتی برخی آسیب پذیریهای امنیتی به صورت ایستا، یعنی بدون اجرای کد استفاده شوند.
در این بخش با برخی از محبوبترین ابزارها برای تجزیه و تحلیل ایستا آشنا خوایم شد. این ابزارها را میتوان در دستههای زیر طبقه بندی کرد: NET، Java، C/C. و Multi-Language. علاوه بر این، این ابزارها منبع باز ویا تجاری هستند.
یکی از ابزارهای تجزیه و تحلیل استاتیک در چارچوب NET. ابزار FxCop است که یک ابزار رایگان ایجاد شده توسط مایکروسافت است. FxCop کد میانی یک مجموعه دات نت کامپایل شده را تجزیه و تحلیل میکند و پیشنهاداتی برای طراحی، امنیت و بهبود عملکرد ارائه میدهد. بهطور پیشفرض، FxCop یک اسمبلی را بر اساس قوانینی که توسط دستورالعملهای طراحی برای توسعه کتابخانههای کلاس تعیین شده است، تجزیه و تحلیل میکند. قوانین دستورالعمل طراحی به 9 دسته تقسیم می شوند، از جمله طراحی، عملکرد و امنیت و غیره. علاوه بر این، FxCop نه تنها بیش از 200 قانون را نمایش میدهد که هنگام تجزیه و تحلیل استفاده میشود، بلکه به کاربر اجازه میدهد قوانین موجود را خاموش کرده و قوانین سفارشی را اضافه کند. FxCop برای توسعه دهندگان کتابخانه کلاس در نظر گرفته شده است اما همچنین به عنوان یک ابزار برای افرادی که تازه وارد چارچوب NET. هستند مفید است.
یک ابزار منبع باز که بهترین قوانین را برای کد جاوا اعمال میکند، به عنوان CheckStyle شناخته می شود. با تجزیه و تحلیل کد منبع جاوا و گزارش هرگونه نقض استانداردها کار می کند. می توان آن را به عنوان یک پلاگین در یک IDE ادغام کرد تا توسعه دهندگان بتوانند فوراً هرگونه نقض استانداردهای رسمی را ببینند و اصلاح کنند. علاوه بر این، میتوان از آن برای تولید گزارشهای کل پروژه که نقضهای یافت شده را خلاصه میکند، استفاده کرد. Checkstyle شامل بیش از 120 قانون و استاندارد است و به مسائلی می پردازد که از قالب بندی کد و قراردادهای نامگذاری تا معیارهای پیچیدگی کد را شامل می شود [16].
ابزار Cppcheck یک ابزار محبوب، منبع باز، رایگان و تجزیه و تحلیل کد ایستا بین پلتفرمی است که به C و C++ اختصاص داده شده است. استفاده از آن آسان است و سادگی آن یکی از مزایای آن است. برای شروع کار با آن نیازی به انجام هیچ گونه تغییر یا اصلاحی ندارید، به همین دلیل است که اغلب برای مبتدیان توصیه می شود. همچنین شهرت دارد که تعداد نسبتاً کمی از موارد مثبت کاذب را گزارش می دهد، یا حداقل این آرزوی ابزار است.
ابزار SonarQube یک نام آشنا در کیفیت کد و امنیت کد است که به همه توسعه دهندگان این امکان را میدهد تا کدهای پاک تر و ایمن تر بنویسند. SonarQube با هزاران قانون خودکار تجزیه و تحلیل کد ایستا در بیش از 25 زبان برنامه نویسی، در حالی که مستقیماً با پلتفرم DevOps شما ادغام میشود، هم تیمی شما برای بهبود گردش کار توسعه و هدایت تیم شما است. SonarQube با ابزارهای موجود شما مطابقت دارد و زمانی که کیفیت یا امنیت پایگاه کد شما در خطر باشد، به طور خودکار، شما را خبر دار میکند. نسخه های مختلف SonarQube را میتوان به صورت رایگان استفاده کرد.
ابزارهایی که برای شناسایی اشکالات در کد منبع استفاده میشوند، اغلب اخطارهای مثبت کاذب زیادی را به کاربر برمیگردانند. هشدارهای مثبت واقعی اغلب در میان تعداد زیادی از مثبت های کاذب باعث حواس پرتی میشوند. با سخت کردن یافتن نکات مثبت واقعی، نرخ مثبت کاذب بالا میتواند کاربران را ناامید کند و آنها را از استفاده از ابزارهای مفید منصرف کند.
ابزارهای خوب تجزیه و تحلیل ایستا، باید به راحتی قابل استفاده باشند. این بدان معناست که نتایج آنها باید برای توسعه دهندگان عادی قابل درک باشد تا کاربران خود را در مورد شیوههای برنامه نویسی خوب آموزش دهند. یکی دیگر از ویژگیهای مهم، نوع دانش (مجموعه قوانین) است که ابزار اعمال میکند. اهمیت یک مجموعه قوانین خوب را نمی توان نادیده گرفت. در پایان، چککنندههای ایستا خوب میتوانند به شناسایی و ریشهکن کردن باگهای امنیتی رایج کمک کنند. این امر به ویژه برای زبان هایی مانند C که مجموعه قوانین بسیار بزرگی برای آنها وجود دارد، بسیار مهم است. تجزیه و تحلیل ایستا باید به طور منظم به عنوان بخشی از هر فرآیند توسعه مدرن اعمال شود.
ابزارهای تجزیه و تحلیل کد ایستا روشی سریع و خودکار برای اطمینان از اینکه کد منبع مطابق با دستورالعمل های طراحی و سبک از پیش تعریف شده باقی میماند، ارائه میدهد. پیروی از چنین دستورالعملهایی به تولید کد یکنواختتر کمک میکند و همچنین میتواند به کاستیهای بالقوه امنیت، عملکرد و قابلیت همکاری و اشاره کند. ابزارهای تجزیه و تحلیل کد ایستا جایگزینی برای بررسی کد به رهبری انسان نیستند. زیرا، با بررسی انسان میتوان در مناطقی که نیاز به توجه بیشتر است، آن مناطق از کد را بیشتر تمرکز کنند.
این مطلب، بخشی از تمرینهای درس معماری نرمافزار در دانشگاه شهیدبهشتی است
مراجع:
1- https://www.checkpoint.com/cyber-hub/cloud-security/what-is-static-code-analysis/
2- Gomes, I.V., Morgado, P., Gomes, T., & Moreira, R.M. (2009). An overview on the Static Code Analysis approach in Software Development.
3- https://www.perforce.com/blog/sca/what-static-analysis