استخدام أدوات XLA

عادةً ما يرتكز سير عمل تطوير XLA على HLO، والذي يمثّل عملية حسابية وظيفية معزولة يتم إرسالها إلى المُجمِّع. تأتي XLA مع أدوات متعددة لصفوف الأوامر (الموضّحة أدناه) التي تستخدِم HLO وتعمل على تشغيلها أو توفير مرحلة compiling (الترجمة) ابتدائية. إنّ استخدام هذه الأدوات مفيد جدًا لدورة تكرار compile->modify->run سريعة، لأنّ لغة HLO قابلة للعرض و قابلة للاختراق، وغالبًا ما يكون تغييرها وتشغيلها بشكلٍ متكرّر هو أسرع طريقة لمحاولة فهم أداء XLA أو سلوكه وحلّ المشاكل المتعلّقة بهما.

إنّ أسهل طريقة للحصول على رمز HLO لبرنامج يتم تجميعه باستخدام XLA هي استخدام متغيّر البيئة XLA_FLAGS عادةً:

$ XLA_FLAGS=--xla_dump_to=/tmp/myfolder ./myprogram-entry-point

الذي يخزّن جميع ملفات HLO قبل التحسين في المجلد المحدّد، بالإضافة إلى العديد من العناصر المفيدة الأخرى.

تشغيل مقتطفات HLO: run_hlo_module

تعمل الأداة run_hlo_module على تحسين HLO قبل التنفيذ، وتجمع تلقائيًا بين تجميع الحِزم وتشغيلها ومقارنتها بتنفيذ المُفسِّر المرجعي. على سبيل المثال، الطلب المعتاد لتشغيل ملف إدخال computation.hlo على وحدة معالجة الرسومات NVIDIA والتحقّق من صحته هو:

$ run_hlo_module --platform=CUDA --reference_platform=Interpreter computation.hlo

كما هو الحال مع جميع الأدوات، يمكن استخدام --help للحصول على القائمة الكاملة للخيارات.

تشغيل مقتطفات HLO مع دعم SPMD: multihost_hlo_runner

أداة تشغيل HLO المتعدّدة المضيفين هي أداة مشابهة جدًا، مع العِلم أنّها تتوافق مع SPMD، بما في ذلك التواصل بين المضيفين. راجِع أداة تشغيل HLO المتعدّدة المضيفين للاطّلاع على التفاصيل.

إعادة تشغيل "طلبات البحث من خادم وكيل" المتعدّدة

يمكن استخدام استدعاءات تتضمّن وحدات متعددة لكل من run_hlo_module وhlo_runner_main، وهو ما ملائم غالبًا لإعادة تشغيل جميع الوحدات في دليل تفريغ البيانات:

$ hlo_runner_main /dump/*before_optimizations*

تنفيذ عمليات الربط/المراحل لتجميع HLO: hlo-opt

عند تصحيح أخطاء المُجمِّع أو فهم آليته، غالبًا ما يكون من المفيد الحصول على التوسيع لأجهزة معيّنة في نقطة معيّنة في مسار التنفيذ (سواء كان HLO أو HLO المحسّن أو TritonIR أو LLVM)، وذلك لinput (مدخل) HLO (مستقر).

يتيح hlo-opt مراحل إخراج متعددة: سواء كانت PTX أو HLO بعد التحسينات أو LLVM IR قبل التحسينات أو TritonIR. تعتمد المجموعة الدقيقة للمراحل المتوافقة على النظام الأساسي (مثلاً، PTX مخصّص لأجهزة NVIDIA)، ويمكن الاطّلاع عليها باستخدام الأمر --list-stages:

$ hlo-opt --platform=CUDA --list-stages
hlo
llvm
ptx

بعد اختيار مرحلة، يمكن للمستخدم كتابة نتيجة التحويل ل منصّة معيّنة إلى بث معيّن:

$ hlo-opt myinput.hlo --platform=CUDA --stage=llvm

سيؤدي ذلك إلى طباعة الذاكرة في stdout (أو في ملف معيّن إذا تم تحديد -o).

الاستخدام بدون جهاز

لا يلزم الوصول إلى وحدة معالجة الرسومات في معظم عمليات الترجمة، ومن خلال تحديد مواصفات وحدة معالجة الرسومات في سطر الأوامر، يمكننا الحصول على مخرجات PTX مثلاً بدون الوصول إلى مسرع:

$ hlo-opt  --platform=CUDA --stage=llvm  --xla_gpu_target_config_filename=(pwd)/tools/data/gpu_specs/a100_pcie_80.txtpb input.hlo

يتم شحن مواصفات وحدات معالجة الرسومات الشائعة مع المُجمِّع، والملف المقدَّم هو تسلسل سلاسل device_description.proto:

gpu_device_info {
  cuda_compute_capability {
    major: 8
    minor: 0
  }
  threads_per_block_limit: 1024
  threads_per_warp: 32
  shared_memory_per_block: 127152
  shared_memory_per_core: 65536
  threads_per_core_limit: 2048
  core_count: 6192
  fpus_per_core: 64
  block_dim_limit_x: 2147483647
  block_dim_limit_y: 65535
  block_dim_limit_z: 65535
  memory_bandwidth: 2039000000000
  l2_cache_size: 4194304
  clock_rate_ghz: 1.1105
  device_memory_size: 79050250240
}
platform_name: "CUDA"

قد تواجه عملية الترجمة بدون جهاز مشاكل إذا كان ضبط الأداء التلقائي مطلوبًا. لحسن الحظ، يمكننا أيضًا تقديم هذه المعلومات في سطر الأوامر:

$ hlo-opt  --platform=CUDA --stage=llvm  --xla_gpu_target_config_filename=gpu_specs/a100_pcie_80.txtpb --xla_gpu_load_autotune_results_from=results.textpb input.hlo

ملف Autotune هو تسلسل نصي لـ autotune_results.proto، ويظهر مثاله على النحو التالي:

version: 3
results {
  device: "CUDA: 8.0, Cores: 108, GPU clock: 1.41 GHz, Memory bandwidth: 1555 GB/s, L2 cache: 40 MB"
  hlo: "{\n  tmp_0 = f16[1,16,17,3]{3,2,1,0} parameter(0)\n  tmp_1 = f16[16,51]{1,0} bitcast(f16[1,16,17,3]{3,2,1,0} tmp_0)\n  tmp_2 = s8[16,17,3]{2,1,0} parameter(1)\n  tmp_3 = s8[51,16]{0,1} bitcast(s8[16,17,3]{2,1,0} tmp_2)\n  tmp_4 = f16[51,16]{0,1} convert(s8[51,16]{0,1} tmp_3)\n  tmp_5 = f16[16,16]{1,0} dot(f16[16,51]{1,0} tmp_1, f16[51,16]{0,1} tmp_4), lhs_contracting_dims={1}, rhs_contracting_dims={0}\n  ROOT tmp_6 = f16[1,16,16]{2,1,0} bitcast(f16[16,16]{1,0} tmp_5)\n}"
  result {
    run_time {
      nanos: 31744
    }
    triton {
      block_m: 32
      block_n: 32
      block_k: 32
      split_k: 1
      num_stages: 1
      num_warps: 4
    }
  }
}

يمكن تسلسل قاعدة بيانات الضبط التلقائي باستخدام XLA_FLAGS=--xla_gpu_dump_autotune_results_t=<myfile.pbtxt>

تشغيل جولة واحدة من المجمع

يمكن أيضًا استخدام العلامات من XLA_FLAGS، لذا يمكن استخدام الأداة لاختبار إجراء جولة واحدة:

$ hlo-opt --platform=CUDA --stage=hlo --passes=algebraic_simplifer input.hlo