کد منبع امن

1. بررسی اجمالی

تکنیک‌های کد منبع امن مجموعه‌ای از شیوه‌هایی هستند که می‌توانند برای بهبود امنیت کد منبع مورد استفاده قرار گیرند. این تکنیک‌ها می‌توانند به شناسایی و رفع آسیب‌پذیری‌ها در کد منبع، جلوگیری از دسترسی غیرمجاز به کد منبع و محافظت از کد منبع در برابر تغییر کمک کنند.

برخی از تکنیک های رایج کد منبع امن عبارتند از:

  • Linting: لینتینگ فرآیند بررسی کد منبع برای خطاها و مسائل سبک است. این کار با استفاده از ابزار lint انجام می شود که برنامه ای است که کد منبع را تجزیه و تحلیل می کند و مشکلات احتمالی را شناسایی می کند. از ابزارهای لینت می توان برای بررسی انواع خطاها، از جمله خطاهای نحوی، خطاهای معنایی، خطاهای سبک و آسیب پذیری های امنیتی استفاده کرد.
  • تست امنیت برنامه استاتیک (SAST): SAST نوعی تست امنیتی است که کد منبع، کد باینری یا کد بایت را برای شناسایی آسیب‌پذیری‌های امنیتی تجزیه و تحلیل می‌کند. ابزارهای SAST می‌توانند برای یافتن آسیب‌پذیری‌ها در انواع زبان‌های برنامه‌نویسی از جمله Go، Java، Python، C++ و C# استفاده شوند.
  • اسکن مجوز: اسکن مجوز فرآیند شناسایی مجوزهای اجزای نرم افزار شخص ثالث مورد استفاده در یک برنامه نرم افزاری است. این مهم است زیرا به اطمینان از مطابقت برنامه با شرایط مجوزها کمک می کند، که می تواند به جلوگیری از مشکلات قانونی کمک کند.

از این تکنیک ها می توان برای بهبود امنیت کد منبع در تمام مراحل چرخه عمر توسعه نرم افزار استفاده کرد. از Linting می توان برای شناسایی خطاها در مراحل اولیه توسعه استفاده کرد، از SAST می توان برای یافتن آسیب پذیری ها قبل از کامپایل یا استقرار کد استفاده کرد، و از اسکن مجوز می توان برای اطمینان از مطابقت برنامه با شرایط مجوزها استفاده کرد.

استفاده از این تکنیک ها می تواند به بهبود امنیت کد منبع و کاهش خطر نقض امنیت کمک کند.

آنچه خواهید آموخت

این آزمایشگاه بر روی ابزارها و تکنیک های ایمن سازی کد منبع نرم افزار تمرکز خواهد کرد.

  • پرز زدن
  • تست امنیت برنامه استاتیک
  • اسکن مجوز

تمام ابزارها و دستورات مورد استفاده در این آزمایشگاه در Cloud Shell انجام می شود.

2. راه اندازی و الزامات

تنظیم محیط خود به خود

  1. به Google Cloud Console وارد شوید و یک پروژه جدید ایجاد کنید یا از یک موجود استفاده مجدد کنید. اگر قبلاً یک حساب Gmail یا Google Workspace ندارید، باید یک حساب ایجاد کنید .

b35bf95b8bf3d5d8.png

a99b7ace416376c4.png

bd84a6d3004737c5.png

  • نام پروژه نام نمایشی برای شرکت کنندگان این پروژه است. این یک رشته کاراکتری است که توسط API های Google استفاده نمی شود. شما می توانید آن را در هر زمان به روز کنید.
  • شناسه پروژه در تمام پروژه‌های Google Cloud منحصربه‌فرد است و تغییرناپذیر است (پس از تنظیم نمی‌توان آن را تغییر داد). Cloud Console به طور خودکار یک رشته منحصر به فرد تولید می کند. معمولاً برای شما مهم نیست که چیست. در اکثر کدها، باید به شناسه پروژه ارجاع دهید (معمولاً به عنوان PROJECT_ID شناخته می شود). اگر شناسه تولید شده را دوست ندارید، ممکن است یک شناسه تصادفی دیگر ایجاد کنید. از طرف دیگر، می‌توانید خودتان را امتحان کنید و ببینید آیا در دسترس است یا خیر. پس از این مرحله نمی توان آن را تغییر داد و در طول مدت پروژه باقی می ماند.
  • برای اطلاع شما، یک مقدار سوم وجود دارد، یک شماره پروژه که برخی از API ها از آن استفاده می کنند. در مورد هر سه این مقادیر در مستندات بیشتر بیاموزید.
  1. در مرحله بعد، برای استفاده از منابع Cloud/APIها باید صورتحساب را در کنسول Cloud فعال کنید . اجرا کردن از طریق این کد لبه نباید هزینه زیادی داشته باشد، اگر اصلاً باشد. برای اینکه منابع را خاموش کنید تا بیش از این آموزش متحمل صورتحساب نشوید، می توانید منابعی را که ایجاد کرده اید حذف کنید یا کل پروژه را حذف کنید. کاربران جدید Google Cloud واجد شرایط برنامه آزمایشی رایگان 300 دلاری هستند.

Cloud Shell Editor را شروع کنید

این آزمایشگاه برای استفاده با Google Cloud Shell Editor طراحی و آزمایش شده است. برای دسترسی به ویرایشگر،

  1. به پروژه Google خود در https://console.cloud.google.com دسترسی پیدا کنید.
  2. در گوشه بالا سمت راست روی نماد ویرایشگر پوسته ابری کلیک کنید

8560cc8d45e8c112.png

  1. یک صفحه جدید در پایین پنجره شما باز می شود
  2. بر روی دکمه Open Editor کلیک کنید

9e504cb98a6a8005.png

  1. ویرایشگر با یک کاوشگر در سمت راست و ویرایشگر در ناحیه مرکزی باز می شود
  2. یک صفحه ترمینال نیز باید در پایین صفحه موجود باشد
  3. اگر ترمینال باز نیست، از کلید ترکیبی «ctrl+» برای باز کردن پنجره ترمینال جدید استفاده کنید

راه اندازی محیط

GOPATH را روی یک فهرست واحد تنظیم کنید تا دستورات مورد استفاده در این آزمایشگاه را ساده کنید.

export GOPATH=$HOME/gopath

یک دایرکتوری برای نگهداری کار ما ایجاد کنید

mkdir -p workspace
cd workspace

مخزن کد منبع را کلون کنید

git clone https://gitlab.com/gcp-solutions-public/shift-left-security-workshop/source-code-lab.git
cd source-code-lab
export WORKDIR=$(pwd)

3. پرز زدن

Linting برای بررسی اشتباهات رایج مبتنی بر سبک یا نقص های مربوط به نحو استفاده می شود. Linting با ارائه یک الگوی نحوی مشترک در چندین تیم که منجر به بررسی سریعتر کد، به اشتراک گذاری دانش و وضوح کد می شود، به امنیت کمک می کند.

علاوه بر این، Linting اشتباهات نحوی رایج را شناسایی می‌کند که می‌تواند منجر به آسیب‌پذیری‌های رایج مانند استفاده نادرست یا کمتر کارآمد از کتابخانه‌ها یا APIهای اصلی شود.

ابزار پیوند staticcheck را نصب کنید

 go get honnef.co/go/tools/cmd/staticcheck@latest

Go Linter (staticcheck) را در دایرکتوری ریشه پروژه اجرا کنید

 staticcheck

خروجی را مرور کنید

main.go:42:29: unnecessary use of fmt.Sprintf (S1039)

شما این خطا را دریافت می کنید زیرا http.ListenAndServe() یک رشته را می پذیرد و کد فعلی از Sprintf بدون ارسال متغیرها به رشته استفاده می کند.

وضعیت خروج فرمان را بررسی کنید.

echo $?

در این حالت، از آنجایی که دستور منجر به خطا شده است، وضعیت خروج 1 یا بیشتر خواهد بود. این روشی است که می تواند در خط لوله CI/CD برای تعیین موفقیت/شکست ابزار استفاده شود.

فایل main.go را ویرایش کنید و کد را اصلاح کنید:

  • خط زیر LINTING - Step 1 در داخل متد main() با افزودن اسلش های اصلی ( // ).
  • دو خط را مستقیماً در زیر LINTING - Step 2 در داخل متد main() با حذف اسلش‌های پیشرو لغو نظر کنید.

staticcheck دوباره در دایرکتوری ریشه پروژه اجرا کنید

staticcheck

این دستور نباید هیچ نتیجه ای (یعنی یک خط خالی) برگرداند.

وضعیت خروج فرمان را بررسی کنید.

  echo $?

در این حالت، از آنجایی که دستور منجر به خطا نمی شود، وضعیت خروج صفر خواهد بود.

4. تست امنیت برنامه استاتیک

تست امنیت AST/Static - تجزیه و تحلیل کد استاتیک را به دنبال نقاط ضعف و مواجهه های رایج ( CWE ) ارائه می دهد.

ابزار AST ( gosec ) را نصب کنید

    export GOSEC_VERSION="2.15.0"
    curl -sfL https://raw.githubusercontent.com/securego/gosec/master/install.sh | \
          sh -s -- -b $(go env GOPATH)/bin v${GOSEC_VERSION}

gosec با فایل سیاست در برابر کد منبع اجرا کنید

gosec -conf policies/gosec-policy.json -fmt=json ./...

خروجی باید مشابه این باشد

{
    "Golang errors": {},
    "Issues": [
        {
            "severity": "HIGH",
            "confidence": "LOW",
            "cwe": {
                "ID": "798",
                "URL": "https://cwe.mitre.org/data/definitions/798.html"
            },
            "rule_id": "G101",
            "details": "Potential hardcoded credentials",
            "file": "/home/random-user-here/shift-left-security-workshop/labs/source-code-lab/main.go",
            "code": "31: \t// STEP 2: Change this and the reference below to something different (ie, not \"pawsword\" or \"password\")\n32: \tvar pawsword = \"im-a-cute-puppy\"\n33: \tfmt.Println(\"Something a puppy would use: \", username, pawsword)\n",
            "line": "32",
            "column": "6"
        }
    ],
    "Stats": {
        "files": 1,
        "lines": 89,
        "nosec": 0,
        "found": 1
    }
}

این ابزار یک مشکل بالقوه را شناسایی کرده است: Potential hardcoded credentials

5. اسکن مجوز

مجوزها برای امنیت مهم هستند زیرا از نظر قانونی می توانند از شما بخواهند کد منبعی را که ممکن است مایل به افشای آن نباشید افشا کنید. این مفهوم مجوزهای " کپی لفت " نامیده می شود که در صورت استفاده از وابستگی با آن مجوزها، از شما می خواهد کد منبع را در معرض نمایش قرار دهید.

golicense نصب کنید

mkdir -p /tmp/golicense
wget -O /tmp/golicense/golicense.tar.gz https://github.com/mitchellh/golicense/releases/download/v0.2.0/golicense_0.2.0_linux_x86_64.tar.gz
pushd /tmp/golicense
tar -xzf golicense.tar.gz
chmod +x golicense
mv golicense $(go env GOPATH)/bin/golicense
popd

فایل باینری را بسازید

go build

بررسی مجوز را با فایل خط مشی فعلی اجرا کنید که مجوزهای "BSD-3-Clause" را مجاز نمی داند

golicense policies/license-policy.hcl hello-world

توجه: این باید با خروجی مشابه شکست بخورد:

 🚫 rsc.io/sampler    BSD 3-Clause "New" or "Revised" License
 🚫 rsc.io/quote      BSD 3-Clause "New" or "Revised" License
 🚫 golang.org/x/text BSD 3-Clause "New" or "Revised" License

برای انتقال "BSD-3-Clause" از لیست deny به لیست allow ، فایل خط مشی policies/license-policy.hcl را تغییر دهید.

بررسی مجوز را دوباره اجرا کنید

golicense policies/license-policy.hcl hello-world

توجه: این باید با خروجی مشابه موفق شود:

    ✅ rsc.io/quote      BSD 3-Clause "New" or "Revised" License
    ✅ rsc.io/sampler    BSD 3-Clause "New" or "Revised" License
    ✅ golang.org/x/text BSD 3-Clause "New" or "Revised" License

6. تبریک می گویم

تبریک می گویم، شما نرم افزار کد را تمام کردید!

آنچه شما آموخته اید

  • ابزارها و تکنیک هایی برای ایمن سازی کد منبع

-

آخرین به روز رسانی: 23/3/23