2727
2828from airflow .decorators import task
2929from airflow .exceptions import AirflowFailException
30- from google .cloud .monitoring_v3 import types
31- import kubernetes
3230
33- from dags .tpu_observability .utils .node_pool_util import Info as node_pool_info
3431from dags .tpu_observability .utils import subprocess_util as subprocess
3532from dags .tpu_observability .utils .gcp_util import query_time_series
33+ from dags .tpu_observability .utils .node_pool_util import Info as node_pool_info
3634from dags .tpu_observability .utils .time_util import TimeUtil
35+ from google .cloud .monitoring_v3 import types
36+ import kubernetes
3737from xlml .utils import gke
3838
3939
@@ -58,25 +58,38 @@ class Workload:
5858 os.environ.setdefault("JAX_USE_PJIT", "true")
5959 jax.distributed.initialize()
6060
61+ idx = jax.process_index()
6162 global_devices = jax.devices()
62- print(
63- f"[Host {jax.process_index()}] "
64- f"Got {len(global_devices)} global devices"
65- )
63+ print(f"[Host {idx}] Got {len(global_devices)} global devices")
6664 mesh = Mesh(global_devices, ("x",))
6765
68- print(f"[Host {jax.process_index()}] Allocating data...")
69- size = 32832
70- x_global = jnp.ones((size, size), dtype=jnp.float32)
71- y_global = jnp.ones((size, size), dtype=jnp.float32)
66+ print(f"[Host {idx}] Allocating data...")
67+ print(f"[Host {idx}] Defining sharding...")
68+ size = 32768
69+ global_shape = (size, size)
70+ sharding = NamedSharding(
71+ mesh, jax.sharding.PartitionSpec("x", None)
72+ )
73+
74+ print(f"[Host {idx}] Creating sharded data directly on devices...")
75+
76+ def ones_callback(index):
77+ resolved_indices = [
78+ s.indices(global_shape[i]) for i, s in enumerate(index)
79+ ]
80+ local_shape = tuple(
81+ stop - start for start, stop, step in resolved_indices
82+ )
83+
84+ return jnp.ones(local_shape, dtype=jnp.float32)
7285
73- print(f"[Host {jax.process_index()}] Sharding data...")
74- sharding = NamedSharding(mesh, jax.sharding.PartitionSpec("x", None))
75- x = jax.device_put(x_global, sharding)
76- y = jax.device_put(y_global, sharding)
77- print(f"[Host {jax.process_index()}] Data on device")
86+ x = jax.make_array_from_callback(
87+ global_shape, sharding, ones_callback)
88+ y = jax.make_array_from_callback(
89+ global_shape, sharding, ones_callback)
90+
91+ print(f"[Host {idx}] Data on device")
7892
79- # ========= Define heavy workload =========
8093 @pjit
8194 def matmul_ultra_heavy(x, y):
8295 tmp1 = jnp.dot(x, y)
@@ -93,7 +106,6 @@ def matmul_ultra_heavy(x, y):
93106 print(f"[Host {jax.process_index()}] Starting benchmark...")
94107
95108 start = time.time()
96- # Remember to control loop time to control experiment time
97109 for i in range(1_000_000):
98110 result = matmul_ultra_heavy(x, y)
99111 result.block_until_ready()
@@ -485,17 +497,18 @@ def delete_one_random_pod(
485497 Defaults to "default".
486498
487499 Raises:
488- AirflowFailException: If no running pods are found in the specified namespace.
500+ AirflowFailException: If no running pods are found in the specified
501+ namespace.
489502 """
490503 running_pods = get_running_pods (node_pool = node_pool , namespace = namespace )
491504 if not running_pods :
492- logging .error (f "No running pods found in namespace: { namespace } " )
505+ logging .error ("No running pods found in namespace: %s" , namespace )
493506 raise AirflowFailException (
494507 f"No running pods found in namespace: { namespace } "
495508 )
496509
497510 target_pod = random .choice (running_pods )
498- logging .info (f "Targeting pod for deletion: { target_pod } " )
511+ logging .info ("Targeting pod for deletion: %s" , target_pod )
499512
500513 with tempfile .NamedTemporaryFile () as temp_config_file :
501514 env = os .environ .copy ()
@@ -509,7 +522,7 @@ def delete_one_random_pod(
509522 ])
510523
511524 subprocess .run_exec (cmd , env = env )
512- logging .info (f "Successfully initiated deletion for pod: { target_pod } " )
525+ logging .info ("Successfully initiated deletion for pod: %s" , target_pod )
513526
514527
515528@task .sensor (poke_interval = 30 , timeout = 900 , mode = "poke" )
@@ -583,8 +596,7 @@ def wait_for_jobset_started(
583596def wait_for_jobset_ttr_to_be_found (
584597 node_pool : node_pool_info , jobset_name : str
585598) -> bool :
586- """
587- Polls the jobset time_between_interruptions metric.
599+ """Polls the jobset time_between_interruptions metric.
588600
589601 A sensor task which polls the jobset time_between_interruptions metric
590602 every 60 seconds for 60 minutes. 60 minutes is used here since this
@@ -594,8 +606,9 @@ def wait_for_jobset_ttr_to_be_found(
594606 impractical for the test to run longer.
595607
596608 Args:
597- info(Info): An instance of the Info class that encapsulates
598- the configuration and metadata of a GKE node pool and workload.
609+ node_pool: An instance of the Info class that encapsulates
610+ the configuration and metadata of a GKE node pool and workload.
611+ jobset_name: The name of the JobSet.
599612 """
600613 now = datetime .datetime .now ()
601614
0 commit comments