การบิลด์ที่กำหนดได้เป็นสิ่งจำเป็นสำหรับการรับรองความถูกต้องของเวิร์กโหลดในสภาพแวดล้อมการดำเนินการที่เชื่อถือได้ (TEE) ของการปรับเปลี่ยนในอุปกรณ์ (ODP) ซึ่งพร้อมให้บริการแก่สาธารณะใน Google Cloud ในชื่อ Confidential Space (CS)
รูปภาพของเวิร์กโหลดต้องสร้างแฮชรูปภาพที่กำหนดได้ซึ่ง CS ใช้สำหรับการรับรองเวิร์กโหลด (ซึ่งใช้สถาปัตยกรรม RFC 9334 Remote ATtestation procedureS (RATS) ของ NIST) ได้
เอกสารนี้จะกล่าวถึงการติดตั้งใช้งานและการรองรับบิลด์ที่กำหนดได้ในที่เก็บ odp-federatedcompute บริการ ODP Aggregator และ Model Updater จะทำงานภายใน Confidential Space ที่เก็บรองรับบิลด์ที่กำหนดได้สำหรับบริการทั้งหมดของเรา ซึ่งจำเป็นสำหรับกรณีการใช้งานในเวอร์ชันที่ใช้งานจริง
บิลด์ที่กำหนด
การสร้างที่กำหนดได้ประกอบด้วยองค์ประกอบหลัก 2 อย่าง ได้แก่
- การคอมไพล์ไบนารีที่จำเป็น ซึ่งรวมถึงไฟล์ JAR, ไลบรารีที่แชร์ และข้อมูลเมตา
- อิมเมจพื้นฐานและการอ้างอิงรันไทม์ อิมเมจพื้นฐานของสภาพแวดล้อมรันไทม์ ที่ใช้เพื่อเรียกใช้ไบนารีที่คอมไพล์แล้ว
ปัจจุบันที่เก็บการประมวลผลแบบรวมของ ODP รองรับภาระงานประเภทต่อไปนี้
- ปริมาณงาน Java + Spring
- TaskAssignment, TaskManagement, Collector
- Java + Spring ที่มีภาระงาน TensorFlow ของ JNI
- ModelUpdater, Aggregator
- ภาระงาน Python
- TaskBuilder
แท็กเริ่มการทำงาน
รายการต่อไปนี้คือการขึ้นต่อกันที่ ODP ใช้เพื่อรักษาความแน่นอน และความพร้อมใช้งาน
- Bazel
- GitHub
- Maven
- PyPi
- สแนปชอต Debian
- รีจิสทรี DockerHub
- Google Container Registry (GCR)
ภาระงานเชิงกำหนด
ภาระงานทั้งหมดได้รับการคอมไพล์โดยใช้ Bazel ด้วย ชุดเครื่องมือเฉพาะภาษาและอิมเมจคอนเทนเนอร์ที่สร้างขึ้นโดยใช้ rules_oci WORKSPACE file จะกำหนดทรัพยากร Dependency ทั้งหมดพร้อมเวอร์ชันและแฮชที่เกี่ยวข้อง
สแนปชอต Debian
ควรสร้างอิมเมจภาระงานทั้งหมดภายใน dockerfile ที่ระบุ สร้างขึ้นบน Debian snapshot สแนปชอตของ Debian มีสแนปชอตของที่เก็บที่เสถียรพร้อมด้วยคุณสมบัติที่กำหนดได้ ดังนี้
- ส่วนหัวและไลบรารีของระบบ
- สถาปัตยกรรมของระบบ
- linux_x86_64
- Debian
- คอมไพเลอร์ C++
ภาระงาน Java Spring
remotejdk_17 ของ Bazel
ใช้เพื่อจัดหา Java ที่ปิดสนิทสำหรับการคอมไพล์ การขึ้นต่อกันอื่นๆ ของ Java จะได้รับการจัดการและกำหนดไว้ในไฟล์ WORKSPACE
ปริมาณงาน Java Spring จะคอมไพล์เป็นไฟล์ JAR ชื่อ
<service>_application.jar โดยในโหลจะมี
- ไฟล์คลาส Java
META-INF/- ข้อมูลไฟล์ Manifest ของ Bazel
build-data.properties- ข้อมูลการสร้าง Bazel
BOOT-INF/- ทรัพยากร Dependency ของ JAR ที่แพ็กเกจซึ่งสร้างโดย rules_spring
เลเยอร์รูปภาพ
อิมเมจของภาระงาน Java Spring ประกอบด้วย 2 เลเยอร์ ดังนี้
- เลเยอร์อิมเมจฐาน
- อิมเมจฐานของ Java
gcr.io/distroless/java17-debian11
- อิมเมจฐานของ Java
- เลเยอร์ภาระงาน
binary_tar.tar<service>_application.jar
การกำหนดค่ารูปภาพ
- จุดแรกเข้า
java -jar <service>_application.jar
ภาระงาน JNI Tensorflow
ภาระงาน JNI Tensorflow สร้างขึ้นบนภาระงาน Java Spring เรามี Toolchain ของ Clang+LLVM Bazel ที่ปิดสนิทโดยใช้ Clang+LLVM 16 ที่สร้างไว้ล่วงหน้าพร้อม sysroot ที่จัดเตรียมโดยอิมเมจสแนปชอตของ Debian เพื่อคอมไพล์โค้ดเครื่อง
โดยปริมาณงาน JNI จะคอมไพล์เป็นไลบรารีที่ใช้ร่วมกันชื่อ libtensorflow.so พร้อมกับ <service>_application.jar
เลเยอร์รูปภาพ
อิมเมจภาระงาน TensorFlow ของ JNI ประกอบด้วยเลเยอร์หลายชั้น ดังนี้
- เลเยอร์อิมเมจฐาน
- อิมเมจฐานของ Java
gcr.io/distroless/java17-debian11
- อิมเมจฐานของ Java
- เลเยอร์ทรัพยากร Dependency ของแพ็กเกจ Debian เลเยอร์สร้างขึ้นโดยใช้ที่เก็บถาวร deb
ที่ดาวน์โหลดจาก debian-snapshot และบรรจุใหม่เป็นเลเยอร์รูปภาพ
libc++1-16_amd64.tarlibc++abi1-16_amd64.tarlibc6_amd64.tarlibunwind-16_amd64.tarlibgcc-s1_amd64.targcc-13-base_amd64.tar
- เลเยอร์ภาระงาน
binary_tar.tar<service>_application.jarlibtensorflow-jni.solibaggregation-jni.so
การกำหนดค่ารูปภาพ
- ป้ายกำกับ (สำหรับรูปภาพที่สร้างขึ้นเพื่อเรียกใช้ภายใน TEE เท่านั้น)
"tee.launch_policy.allow_env_override": "FCP_OPTS"- อนุญาตให้
FCP_OPTSตั้งค่าตัวแปรสภาพแวดล้อมในพื้นที่ ที่เป็นความลับ เวิร์กโหลดจะใช้FCP_OPTSเมื่อเริ่มต้นเพื่อกำหนดค่า พารามิเตอร์ที่จำเป็น - ระบบจะตั้งค่าตัวแปรสภาพแวดล้อม
FCP_OPTSเมื่อเรียกใช้รูปภาพ (แทนที่จะสร้าง) เพื่อรักษาการกำหนดบิลด์
- อนุญาตให้
"tee.launch_policy.log_redirect": "always""tee.launch_policy.monitoring_memory_allow": "always"
- จุดแรกเข้า
java -Djava.library.path=. -jar <service>_application.jar
ภาระงาน Python
rules_python ของ Bazel ใช้เพื่อ จัดหาเครื่องมือ Python 3.10 ที่ปิดสนิท ระบบจะใช้ไฟล์ requirements ของ pip ที่ล็อกไว้ เพื่อดึงข้อมูลทรัพยากร Dependency ของ pip อย่างแน่นอน อิมเมจสแนปชอต Debian ช่วยให้มั่นใจได้ว่าระบบจะดึงข้อมูลการกระจายที่กำหนดไว้ตามความเข้ากันได้ของแพลตฟอร์ม และมีเครื่องมือ C++ สำหรับคอมไพล์การกระจายซอร์ส
ระบบจะแพ็กเกจภาระงาน Python เป็นชุดแพ็กเกจ pip ที่ดาวน์โหลด การกระจาย Python 3.10 ซอร์สโค้ด ODP Python และสคริปต์เริ่มต้น Python
<service>.runfiles/- ระบบจะจัดเก็บการกระจาย Python ไว้ใน
python_x86_64-unknown-linux-gnu/ - ซอร์สโค้ดจะจัดเก็บไว้ใน
com_google_ondevicepersonalization_federatedcompute/ - แพ็กเกจ Pip จะจัดเก็บไว้ใน
pypi_<dependency_name>/
- ระบบจะจัดเก็บการกระจาย Python ไว้ใน
<service>.runfiles_manifest- ไฟล์ Manifest สำหรับไดเรกทอรี
<service>.runfiles/
- ไฟล์ Manifest สำหรับไดเรกทอรี
<service>- สคริปต์ Python เพื่อเรียกใช้เวิร์กโหลด Python โดยใช้ไฟล์ที่เรียกใช้
เลเยอร์รูปภาพ
อิมเมจเวิร์กโหลด Python ประกอบด้วย 4 เลเยอร์ ดังนี้
- เลเยอร์อิมเมจฐาน
- อิมเมจพื้นฐานของ Python python:slim
- เลเยอร์ล่าม
interpreter_layer.jar<service>/<service>.runfiles/python_x86_64-unknown-linux-gnu/**
- เลเยอร์แพ็กเกจ
packages_layer.jar<service>/<service>.runfiles/**/site-packages/**
- เลเยอร์ภาระงาน
app_tar_manifest.tar- มีซอร์สโค้ด สคริปต์เริ่มต้น และไฟล์ Manifest
<service>/<service>.runfiles_manifest<service>/<service><service>/<service>.runfiles/com_google_ondevicepersonalization_federatedcompute/**
- มีซอร์สโค้ด สคริปต์เริ่มต้น และไฟล์ Manifest
การกำหนดค่ารูปภาพ
- จุดแรกเข้า
/<service>/<service>
สร้างอิมเมจ
เมื่อเลือกภาระงานแล้ว คุณก็พร้อมที่จะสร้างและเผยแพร่ อิมเมจ
ข้อกำหนดเบื้องต้น
ขั้นตอน
ควรสร้างรูปภาพภายในคอนเทนเนอร์ Docker ที่สร้างโดย dockerfile ที่ระบุ เรามีสคริปต์ 2 รายการเพื่อช่วยในการสร้างอิมเมจที่กำหนดได้สุดท้าย
- docker_run.sh
docker_run.shจะสร้างอิมเมจ Docker จาก Dockerfile, เมานต์ ไดเรกทอรีงาน, เมานต์แดมอน Docker ของโฮสต์ และเรียกใช้ Docker ด้วย คำสั่ง Bash ที่ระบุ ตัวแปรที่ส่งก่อนคำสั่ง Bash จะถือเป็นแฟล็ก docker run
- build_images.sh
build_images.shจะเรียกใช้bazel buildสำหรับรูปภาพทั้งหมดและแสดงผล แฮชของรูปภาพที่สร้างขึ้นสำหรับรูปภาพแต่ละรูปที่สร้างขึ้น
สร้างอิมเมจทั้งหมด
./scripts/docker/docker_run.sh "./scripts/build_images.sh"
คุณดูแฮชของรูปภาพที่คาดไว้สำหรับการเผยแพร่แต่ละครั้งได้ที่ส่วน odp-federatedcompute GitHub releases
เผยแพร่รูปภาพ
การเผยแพร่ได้รับการกำหนดค่าโดยใช้กฎ Bazel ของ oci_push สำหรับแต่ละบริการ ควรตั้งค่าที่เก็บเป้าหมายสำหรับ ทั้งหมดดังนี้
- ผู้รวบรวมข้อมูล
- ผู้รวบรวม
- model_updater
- task_assignment
- task_management
- task_scheduler
- task_builder
เผยแพร่รูปภาพเดียว
วิธีเผยแพร่รูปภาพเดียว
./scripts/docker/docker_run.sh "bazel run //shuffler/services/<servicename_no_underscore>:<servicename_with_underscore>_image_publish"
รูปภาพที่สร้างขึ้น
ครีเอเตอร์จะต้องจัดเก็บและโฮสต์รูปภาพที่สร้างขึ้นทั้งหมด เช่น ใน ที่เก็บอาร์ติแฟกต์ของ GCP