Güvenli Alan codelab'i

1. Genel Bakış

GPU hızlandırmalı iş yüklerinizin güvenliğini ve gizliliğini artırmaya hazır mısınız? Bu kod laboratuvarı, hassas yapay zeka/makine öğrenimi iş yüklerinizde güçlü operatör izolasyonu ve hızlandırıcı desteği sağlayan bir teklif olan Trusted Space'ın özellikleri konusunda size yol gösterecektir.

Değerli verileri, modelleri ve anahtarları korumak her zamankinden daha önemli. Güvenli Alan, iş yüklerinizin iş yükü operatörünün bile erişemeyeceği güvenli ve güvenilir bir ortamda çalışmasını sağlayarak bir çözüm sunar.

Güvenilir Alan'ın sunduğu avantajlar:

  • Gelişmiş Gizlilik ve Güvenlik: Güvenli Alan, hassas öğelerinizin (ör. modeller, değerli veriler ve anahtarlar) şifreleme kanıtıyla desteklenen bir şekilde korunduğu güvenilir bir yürütme ortamı sağlar.
  • Operatör yalıtımı: Operatör müdahalesiyle ilgili endişeleri ortadan kaldırın. Güvenli Alan sayesinde, iş yükü operatörleriniz bile erişemez. Bu sayede, SSH kullanmalarını, verilere erişmelerini, yazılım yüklemelerini veya kodunuzu değiştirmelerini engellersiniz.
  • Hızlandırıcı Desteği: Güvenli Alan, H100, A100, T4 ve L4 gibi GPU'lar da dahil olmak üzere çok çeşitli donanım hızlandırıcılarla sorunsuz şekilde çalışacak şekilde tasarlanmıştır. Bu sayede, performans açısından kritik olan yapay zeka/makine öğrenimi uygulamalarınızın sorunsuz şekilde çalışması sağlanır.

Neler öğreneceksiniz?

  • Güvenilir Alan'ın temel tekliflerini öğrenin.
  • Yapay zeka/makine öğrenimi iş yükünüzün değerli öğelerini korumak için Güvenli Alan ortamını nasıl dağıtacağınızı ve yapılandıracağınızı öğrenin.

Gerekenler

Primus Company ile Hassas Kod Oluşturma İstemlerini Koruma

Bu kod laboratuvarında, çalışanlarının verilerinin gizliliğine ve güvenliğine öncelik veren Primus adlı bir şirketin yerine geçeceğiz. Primus, geliştiricilerinin kodlama görevlerine yardımcı olmak için bir kod oluşturma modeli dağıtmak istiyor. Ancak bu istemler genellikle hassas kod snippet'leri, dahili proje ayrıntıları veya tescilli algoritmalar içerdiğinden, çalışanları tarafından gönderilen istemlerin gizliliğini koruma konusunda endişeleri var.

Primus şirketi operatöre neden güvenmiyor?

Primus Corp, oldukça rekabetçi bir pazarda faaliyet gösteriyor. Kod tabanları, rekabet avantajı sağlayan özel algoritmalar ve hassas kod snippet'leri de dahil olmak üzere değerli fikri mülk içerir. İş yükü operatörleri tarafından şirket casusluğu yapılabileceğinden endişe duyuyor. Ayrıca çalışan istemleri, Primus Corp'un korumak istediği gizli "Bilgilendirilmesi Gereken" kod bölümlerini içerebilir.

Primus Corp, bu endişeyi gidermek için kod oluşturma amacıyla modeli çalıştıran çıkarım sunucusunu izole etmek üzere Güvenli Alan'dan yararlanacaktır. İşleyiş şekli:

  • İstem şifreleme: Her çalışan, çıkarım sunucusuna istem göndermeden önce istemi Google Cloud'da Primus Corp tarafından yönetilen bir KMS anahtarı kullanarak şifreler. Bu sayede, şifre çözme anahtarının bulunduğu Güvenli Alan ortamının şifreyi çözmesi ve açık metin istemlerine erişmesi sağlanır. Gerçek dünyadaki bir senaryoda istemci tarafı şifreleme, mevcut kitaplıklar (ör. tink) tarafından yönetilebilir. Bu codelab kapsamında, zarf şifrelemesi ile bu örnek istemci uygulamasını kullanacağız.
  • Operatör izolasyonu: Şifreleme için kullanılan anahtara yalnızca Güvenli Alan ortamında çalışan çıkarım sunucusu erişebilir ve istemlerin şifresini güvenilir bir ortamda çözebilir. Şifreleme anahtarına erişim, Workload Identity havuzu tarafından korunur. Güvenli Alan'ın yalıtım garantileri sayesinde, iş yükü operatörü bile şifreleme için kullanılan anahtara ve şifresi çözülmüş içeriğe erişemez.
  • Hızlandırıcılar kullanarak güvenli çıkarım: Çıkarma sunucusu, Güvenli alan kurulumunun bir parçası olarak Korumalı Sanal Makine'de başlatılır. Bu sayede, iş yükü örneğinin başlatma veya çekirdek düzeyinde kötü amaçlı yazılım ya da rootkit'ler tarafından güvenliğinin ihlal edilmediğinden emin olabilirsiniz. Bu sunucu, Güvenli Alan ortamındaki istemin şifresini çözer, kod oluşturma modelini kullanarak çıkarım yapar ve oluşturulan kodu çalışana döndürür.

2. Cloud kaynaklarını ayarlama

Başlamadan önce

  • Bu kod laboratuvarının bir parçası olarak kullanılan gerekli komut dosyalarını almak için aşağıdaki komutu kullanarak bu depoyu klonlayın.
git clone https://github.com/GoogleCloudPlatform/confidential-space.git
  • Bu kod laboratuvarının dizinini değiştirin.
cd confidential-space/codelabs/trusted_space_codelab/scripts
  • Gerekli proje ortam değişkenlerini aşağıda gösterildiği gibi ayarladığınızdan emin olun. GCP projesi oluşturma hakkında daha fazla bilgi için lütfen bu kod laboratuvarını inceleyin. Proje kimliğinin nasıl alınacağı ve proje adından ve proje numarasından nasıl farklı olduğu hakkında ayrıntılı bilgi edinmek için bu makaleyi inceleyebilirsiniz.
export PRIMUS_PROJECT_ID=<GCP project id of Primus>
gcloud services enable \
    cloudapis.googleapis.com \
    cloudresourcemanager.googleapis.com \
    cloudkms.googleapis.com \
    cloudshell.googleapis.com \
    container.googleapis.com \
    containerregistry.googleapis.com \
    iam.googleapis.com \
    confidentialcomputing.googleapis.com
  • Aşağıdaki komutu kullanarak yukarıda belirtilen kaynak adları için değişkenlere değer atayın. Bu değişkenler, kaynak adlarını gerektiği gibi özelleştirmenize ve daha önce oluşturulmuş mevcut kaynakları kullanmanıza olanak tanır. (ör.export PRIMUS_SERVICE_ACCOUNT='my-service-account')
  1. Primus projesinde aşağıdaki değişkenleri mevcut bulut kaynağı adlarıyla ayarlayabilirsiniz. Değişken ayarlanırsa Primus projesindeki ilgili mevcut bulut kaynağı kullanılır. Değişken ayarlanmamışsa bulut kaynağı adı, proje adından oluşturulur ve bu adla yeni bir bulut kaynağı oluşturulur. Kaynak adları için desteklenen değişkenler şunlardır:

$PRIMUS_PROJECT_REGION

Primus şirketi için bölgesel kaynakların oluşturulacağı bölge.

$PRIMUS_SERVICE_LOCATION

Primus şirketi için kaynakların oluşturulacağı konum.

$PRIMUS_PROJECT_ZONE

Primus şirketi için bölgesel kaynakların oluşturulacağı bölge.

$PRIMUS_WORKLOAD_IDENTITY_POOL

Primus şirketinin bulut kaynaklarını korumak için kullandığı Workload Identity Pool.

$PRIMUS_WIP_PROVIDER

Primus şirketinin, Attestation Verifier Service tarafından imzalanan jetonlar için kullanılacak yetkilendirme koşulunu içeren Workload Identity Pool sağlayıcısı.

$PRIMUS_SERVICEACCOUNT

Primus şirketinin, $PRIMUS_WORKLOAD_IDENTITY_POOL'ın korumalı kaynaklara erişmek için kullandığı hizmet hesabı. Bu adımda, $PRIMUS_INPUT_STORAGE_BUCKET veri grubunda depolanan müşteri verilerini görüntüleme izni vardır.

$PRIMUS_ENC_KEY

KMS anahtarı, Primus şirketinin çalışanları tarafından sağlanan istemleri şifrelemek için kullanılır.

$PRIMUS_ENC_KEYRING

Primus şirketi için $PRIMUS_ENC_KEY şifreleme anahtarını oluşturmak üzere kullanılacak KMS anahtar zinciri.

$PRIMUS_ENC_KEYVERSION

$PRIMUS_ENC_KEY şifreleme anahtarının KMS anahtar sürümü. Varsayılan değer 1'dir. Geçmişte döndürülmüş ve sürümü güncellenmiş mevcut bir anahtar kullanıyorsanız bunu güncelleyin.

$PRIMUS_ARTIFACT_REPOSITORY

İş yükü Docker resminin itileceği yapı deposu.

$PRIMUS_PROJECT_REPOSITORY_REGION

Yayınlanan iş yükü Docker görüntüsünün bulunduğu yapı deposunun bölgesi.

$WORKLOAD_VM

İş yükü sanal makinesinin adı.

$WORKLOAD_IMAGE_NAME

İş yükü Docker görüntüsünün adı.

$WORKLOAD_IMAGE_TAG

İş yükü kapsayıcı resminin etiketi.

$WORKLOAD_SERVICEACCOUNT

İş yükünü çalıştıran Gizli Sanal Makine'ye erişme izni olan hizmet hesabı.

$CLIENT_VM

Tahmin sunucusunun istemci uygulamasını çalıştıracak istemci sanal makinesinin adı.

$CLIENT_SERVICEACCOUNT

$CLIENT_VM tarafından kullanılan hizmet hesabı

  • $PRIMUS_PROJECT_ID projesi için Depolama Alanı Yöneticisi, Artifact Registry Yöneticisi, Cloud KMS Yöneticisi, Hizmet Hesabı Yöneticisi, IAM Workload Identity Pool Yöneticisi rollerine sahip olmanız gerekir. GCP Console'u kullanarak IAM rolleri verme hakkında bu kılavuzu inceleyebilirsiniz.
  • $PRIMUS_PROJECT_ID için, kalan değişken adlarını kaynak adları için proje kimliğinize göre değerlere ayarlamak üzere aşağıdaki komut dosyasını çalıştırın.
source config_env.sh

Primus Company kaynaklarını ayarlama

Bu adımda, Primus için gerekli bulut kaynaklarını ayarlarsınız. Primus için kaynakları ayarlamak üzere aşağıdaki komut dosyasını çalıştırın. Komut dosyası yürütme kapsamında aşağıdaki kaynaklar oluşturulur:

  • Primus şirketinin müşteri verileri dosyasını şifrelemek için KMS'deki şifreleme anahtarı ($PRIMUS_ENC_KEY) ve anahtar zinciri ($PRIMUS_ENC_KEYRING).
  • Workload Identity Pool ($PRIMUS_WORKLOAD_IDENTITY_POOL), sağlayıcısı altında yapılandırılan özellik koşullarına göre iddiaları doğrulamak için kullanılır.
  • Yukarıda belirtilen iş yükü kimlik havuzuna ($PRIMUS_WORKLOAD_IDENTITY_POOL) bağlı hizmet hesabı ($PRIMUS_SERVICE_ACCOUNT), KMS anahtarını kullanarak verilerin şifresini çözme (roles/cloudkms.cryptoKeyDecrypter rolünü kullanarak), KMS anahtarını kullanarak verileri şifreleme (roles/cloudkms.cryptoKeyEncrypter rolünü kullanarak), Cloud Storage paketinden veri okuma (objectViewer rolünü kullanarak) ve hizmet hesabını iş yükü kimlik havuzuna bağlama (roles/iam.workloadIdentityUser rolünü kullanarak) erişimine sahiptir.
./setup_primus_resources.sh

3. İş Yükü Oluşturma

İş yükü hizmet hesabı oluşturma

Artık iş yükü için gerekli rollere ve izinlere sahip bir hizmet hesabı oluşturacaksınız. Primus projesinde iş yükü hizmet hesabı oluşturmak için aşağıdaki komut dosyasını çalıştırın. Bu hizmet hesabı, çıkarım sunucusunu çalıştıran sanal makine tarafından kullanılır.

Bu iş yükü hizmet hesabı ($WORKLOAD_SERVICEACCOUNT) aşağıdaki rollere sahip olacaktır:

  • confidentialcomputing.workloadUser onay jetonu almak için
  • logging.logWriter kullanarak Cloud Logging'e günlük yazabilirsiniz.
./create_workload_service_account.sh

İş yükü oluşturma

Bu adımda, iş yükü Docker görüntüsü oluşturacaksınız. İş yükü Primus şirketi tarafından oluşturulur. Bu codelab'de kullanılan iş yükü, herkese açık GCS paketinden (vertex model bahçesinden) codegemma modelini kullanan Python kodudur. İş yükü, codegemma modelini yükler ve Primus geliştiricilerinden gelen kod oluşturma isteklerini sunacak çıkarım sunucusunu başlatır.

Workload, kod oluşturma isteğinde şifrelenmiş bir istemle birlikte sarmalanmış DEK'yi alır. Ardından iş yükü, DEK'nin şifresini çözmek için KMS API çağrısı yapar ve bu DEK'yi kullanarak istemin şifresini çözer. Şifreleme anahtarları (DEK için) iş yükü kimliği havuzu aracılığıyla korunur ve özellik koşullarını karşılayan iş yükleri için erişim izni verilir. Bu özellik koşulları, iş yükü için yetkilendirmeyle ilgili bir sonraki bölümde daha ayrıntılı olarak açıklanmıştır. Tahmin sunucusu şifresi çözülmüş istemi aldıktan sonra, yüklü bir modeli kullanarak kodu oluşturur ve yanıtı döndürür.

Aşağıdaki adımların uygulandığı bir iş yükü oluşturmak için aşağıdaki komut dosyasını çalıştırın:

  • Primus'a ait bir Artifact Registry($PRIMUS_ARTIFACT_REGISTRY) oluşturun.
  • İş yükü kodunu gerekli kaynak adlarıyla güncelleyin.
  • Tahmin sunucusu iş yükünü derleyin ve iş yükü kodunun Docker görüntüsünü oluşturmak için Dockerfile oluşturun. Bu codelab için kullanılan Dockerfile'i burada bulabilirsiniz.
  • Docker görüntüsünü oluşturun ve Primus'un sahip olduğu Artifact Registry'de ($PRIMUS_ARTIFACT_REGISTRY) yayınlayın.
  • $WORKLOAD_SERVICEACCOUNT kullanıcısına $PRIMUS_ARTIFACT_REGISTRY için okuma izni verin. Bu, iş yükü kapsayıcısının iş yükü Docker görüntüsünü Artifact Registry'den çekmesi için gereklidir.
./create_workload.sh

Bu codelab'de oluşturulup kullanılan iş yükünün generate() yöntemini referans olarak burada bulabilirsiniz (İş yükü kodunun tamamını burada bulabilirsiniz).

def generate():
  try:
    data = request.get_json()
    ciphertext = base64.b64decode(data["ciphertext"])
    wrapped_dek = base64.b64decode(data["wrapped_dek"])
    unwrapped_dek_response = kms_client.decrypt(
        request={"name": key_name, "ciphertext": wrapped_dek}
    )
    unwrapped_dek = unwrapped_dek_response.plaintext
    f = Fernet(unwrapped_dek)
    plaintext = f.decrypt(ciphertext)
    prompt = plaintext.decode("utf-8")
    tokens = tokenizer(prompt, return_tensors="pt")
    outputs = model.generate(**tokens, max_new_tokens=128)
    generated_code = tokenizer.decode(outputs[0])
    generated_code_bytes = generated_code.encode("utf-8")

    response = f.encrypt(generated_code_bytes)
    ciphertext_base64 = base64.b64encode(response).decode("utf-8")
    response = {"generated_code_ciphertext": ciphertext_base64}
    return jsonify(response)

  except (ValueError, TypeError, KeyError) as e:
    return jsonify({"error": str(e)}), 500

4. İş yükünü yetkilendirme ve çalıştırma

İş yükünü yetkilendirme

Primus, aşağıdaki kaynakların özelliklerine göre anında şifreleme için kullanılan KMS anahtarlarına erişmeleri amacıyla iş yüklerine yetki vermek istiyor:

  • Nedir?: Doğrulanan kod
  • Nerede: Güvenli bir ortam
  • Who: Güvenilir bir operatör

Primus, bu şartlara dayalı bir erişim politikasını zorunlu kılmak için Workload Identity federasyonu'nu kullanır. İş yükü kimliği federasyonu, özellik koşullarını belirtmenize olanak tanır. Bu koşullar, iş yükü kimliği havuzu (WIP) ile hangi kimliklerin kimlik doğrulaması yapabileceğini kısıtlar. Ölçümleri sunmak ve politikayı uygulamak için Attestation Verifier Hizmeti'ni WIP'ye workload identity pool sağlayıcısı olarak ekleyebilirsiniz.

Workload Identity havuzu, bulut kaynakları kurulum adımı kapsamında daha önce oluşturulmuştur. Primus, yeni bir OIDC Workload Identity Pool sağlayıcısı oluşturur. Belirtilen --attribute-condition, iş yükü kapsayıcısına erişimi yetkilendirir. Bunun için:

  • Ne: $PRIMUS_ARTIFACT_REPOSITORY deposuna yüklenen en son $WORKLOAD_IMAGE_NAME.
  • Kullanılabileceği yerler: Gizli Alan güvenilir yürütme ortamı, tam destekli Gizli Alan sanal makine görüntüsünde çalışır.
  • Kim: Primus $WORKLOAD_SERVICE_ACCOUNT hizmet hesabı.
export WORKLOAD_IMAGE_DIGEST=$(gcloud artifacts docker images describe ${PRIMUS_PROJECT_REPOSITORY_REGION}-docker.pkg.dev/$PRIMUS_PROJECT_ID/$PRIMUS_ARTIFACT_REPOSITORY/$WORKLOAD_IMAGE_NAME:$WORKLOAD_IMAGE_TAG  --format="value(image_summary.digest)" --project ${PRIMUS_PROJECT_ID})
gcloud iam workload-identity-pools providers create-oidc $PRIMUS_WIP_PROVIDER \
  --location="global" \
  --project="$PRIMUS_PROJECT_ID" \
  --workload-identity-pool="$PRIMUS_WORKLOAD_IDENTITY_POOL" \
  --issuer-uri="https://confidentialcomputing.googleapis.com/" \
  --allowed-audiences="https://sts.googleapis.com" \
  --attribute-mapping="google.subject='assertion.sub'" \
  --attribute-condition="assertion.swname == 'HARDENED_SHIELDED' && assertion.hwmodel == 'GCP_SHIELDED_VM' && 
assertion.submods.container.image_digest == '${WORKLOAD_IMAGE_DIGEST}' &&
 assertion.submods.container.image_reference == '${PRIMUS_PROJECT_REPOSITORY_REGION}-docker.pkg.dev/$PRIMUS_PROJECT_ID/$PRIMUS_ARTIFACT_REPOSITORY/$WORKLOAD_IMAGE_NAME:$WORKLOAD_IMAGE_TAG' && 
'$WORKLOAD_SERVICEACCOUNT@$PRIMUS_PROJECT_ID.iam.gserviceaccount.com' in assertion.google_service_accounts"

Yukarıdaki komut, hwmodel değerinin "GCP_SHIELDED_VM" ve swname değerinin "HARDENED_SHIELDED" olarak ayarlanıp ayarlanmadığını kontrol ederek iş yükünün güvenilir bir alan ortamında çalıştığını doğrular. Ayrıca, güvenliği artırmak ve çalışan iş yükünün bütünlüğünü sağlamak için image_digest ve image_reference gibi iş yüküne özgü iddialar içerir.

İş yükünü çalıştırma

Bu adım kapsamında, iş yükünü bir hızlandırıcının bağlı olduğu Güvenli Alan sanal makinesinde çalıştıracağız. Zorunlu TEE bağımsız değişkenleri, meta veri işareti kullanılarak iletilir. İş yükü kapsayıcısıyla ilgili bağımsız değişkenler, işaretin "tee-cmd" kısmı kullanılarak iletilir. İş yükü sanal makinesini Nvidia Tesla T4 GPU ile donatmak için --accelerator=type=nvidia-tesla-t4,count=1 işaretini kullanırız. Bu işlem, sanal makineye bir GPU ekler. Ayrıca, uygun GPU sürücüsünün yüklenmesini tetiklemek için meta veri işaretlerine tee-install-gpu-driver=true eklememiz gerekir.

gcloud compute instances create ${WORKLOAD_VM} \
  --accelerator=type=nvidia-tesla-t4,count=1 \
  --machine-type=n1-standard-16 \
  --shielded-secure-boot \
  --image-project=conf-space-images-preview \
  --image=confidential-space-0-gpupreview-796705b \
  --zone=${PRIMUS_PROJECT_ZONE} \
  --maintenance-policy=TERMINATE \
  --boot-disk-size=40 \
  --scopes=cloud-platform \
  --service-account=${WORKLOAD_SERVICEACCOUNT}@${PRIMUS_PROJECT_ID}.iam.gserviceaccount.com \
  --metadata="^~^tee-image-reference=${PRIMUS_PROJECT_REPOSITORY_REGION}-docker.pkg.dev/${PRIMUS_PROJECT_ID}/${PRIMUS_ARTIFACT_REPOSITORY}/${WORKLOAD_IMAGE_NAME}:${WORKLOAD_IMAGE_TAG}~tee-install-gpu-driver=true~tee-restart-policy=Never"

Çıkarsama Sorgusu Çalıştırma

İş yükü çıkarım sunucusu başarıyla kullanıma sunulduktan sonra Primus şirketinin çalışanları, kod oluşturma isteklerini çıkarım sunucusuna gönderebilir.

Bu codelab'in bir parçası olarak, çıkarım sunucusuyla etkileşime geçecek istemci uygulamasını ayarlamak için aşağıdaki komut dosyasını kullanacağız. İstemci sanal makinesini ayarlamak için bu komut dosyasını çalıştırın.

./setup_client.sh

Aşağıdaki adımlarda, istemci sanal makinesine SSH'nin nasıl bağlanacağı ve Python sanal ortamında örnek bir istemci uygulamasının nasıl çalıştırılacağı gösterilmektedir. Bu örnek uygulamada, Fernet kitaplığıyla zarf şifrelemesi kullanılmaktadır. Ancak belirli şifreleme kitaplıklarının farklı kullanım alanlarına uyacak şekilde uyarlanabileceğini unutmayın.

gcloud compute ssh ${CLIENT_VM} --zone=${PRIMUS_PROJECT_ZONE}

İstemci sanal makinesinde Python sanal ortamını etkinleştirmek ve istemci uygulamasını yürütmek için aşağıdaki komutları çalıştırın.

source venv/bin/activate
python3 inference_client.py

Bu örnek istemci uygulamasının çıkışında, şifreleme ve düz metin istemi istekleri ile bunların şifrelenmiş ve şifresi çözülmüş yanıtları gösterilir.

5. Temizleme

Bu codelab kapsamında oluşturduğumuz kaynakları temizlemek için kullanılabilecek komut dosyası burada verilmiştir. Bu temizleme kapsamında aşağıdaki kaynaklar silinecek:

  • Primus hizmet hesabı ($PRIMUS_SERVICEACCOUNT).
  • Primus şifreleme anahtarı ($PRIMUS_ENC_KEY).
  • Primus'un yapı deposu ($PRIMUS_ARTIFACT_REPOSITORY).
  • Sağlayıcısıyla birlikte Primus iş yükü kimliği havuzu ($PRIMUS_WORKLOAD_IDENTITY_POOL).
  • Primus'un ($WORKLOAD_SERVICEACCOUNT) iş yükü hizmet hesabı.
  • İş yükü sanal makinesi ($WORKLOAD_VM) ve istemci sanal makinesi ($CLIENT_VM).
./cleanup.sh

Keşif yapmayı tamamladıysanız lütfen projenizi silin.

  • Cloud Platform Console'a gidin.
  • Kapatmak istediğiniz projeyi seçin, ardından en üstteki "Sil"i tıklayın: Bu işlem, projenin silinmesi için planlama yapar.